carfield.com.hkChainOfResponsibilityProtocol.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.patterns.
*
* Contributor(s):
*/
import java.util.WeakHashMap;
/**
* Defines the general behavior of the chain of responsibility design pattern.
*
* Each concrete sub-aspect of this aspect defines one particular instance of
* the pattern, with an arbitrary number of <i>Handler</i> classes involved.
*
* The sub-aspect defines three things: <ol>
*
* <li> what types can be handlers
*
* <li> what triggers an event to be raised
*
* <li> how each <i>Handler</i> treats a particular event. The default
* implementation in this aspect here makes it only necessary to code
* those cases where an event is actually handled.
* </ol>
*
* Note that in this implementation, a default behavior for <i>Handler</i>s is
* defined: unless a <i>Handler</i> explicitly handles an event, it is passed
* to its successor. In addition to that, the implementation allows to define
* a default bahavior in case no <i>Handler</i> in the chain handles an event.
* Here, an error message is shown. <p>
*
* Note further that this version does not define a <i>Request</i> role.
* Although that would be a more consistent approach, AspectJ does not allow
* the mechanisms used here if the code is not accessible by <code>ajc</code>.
* Thus, the pointcuts would not match appropriately. A solution would be to
* Subclass all potential Objects, but that seems to be unneccessarily
* complex.
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.0, 05/13/02
*
*/
public abstract aspect ChainOfResponsibilityProtocol {
/**
* true if the notification mode is on, false otherwise
*/
protected boolean notificationOn = false;
/**
* This interface is used by extending aspects to say what types
* handle requests. It models the <i>Handler</i> role.
*/
protected interface Handler {}
/**
* Stores the mapping between <code>Handler</code>s and its<i>
* Successor</i>. For each handler, its <i>Successor</i>
* is stored.
*/
public WeakHashMap successors = new WeakHashMap();
/**
* Implements the abstracted CoR behavior. Assumption: If the request is
* not handled, the last receiver handles it by default ( that is true
* for this implementnation of the protocol).
*
* The current handler gets asked if it wants to handle the request. If
* not, the request is forwarded to its successor
*/
protected void receiveRequest(Handler handler, Object request) {
note("Call received for: "+handler.getClass().getName());
if (handler.acceptRequest(request)) {
note("Class "+handler.getClass().getName()+" is accepting the request");
handler.handleRequest(request);
note("Call handled.\n");
} else {
note("Class "+handler.getClass().getName()+" is rejecting the request");
Handler successor = getSuccessor(handler);
if (successor == null) {
note("Request unhandled!\n");
} else {
note("Call forwarded to: "+successor.getClass().getName());
receiveRequest(successor, request);
}
}
}
/**
* Method attached to Handlers: returns true if a Handler wants to hanlde
* that request. By default, requests are rejected.
*
* @param request the request to be handled
*/
public boolean Handler.acceptRequest(Object request) {
System.out.println("Default reject: event from "+this.getClass().getName());
return false;
}
/**
* Method attached to Handlers: handles a request. Default implementation
* does nothing, only shows an error message.
*
* @param request the request to be handled
*/
public void Handler.handleRequest(Object request) { // The Event is not handled elsewhere
System.out.println("No successor, request ignored");
}
/**
* The join points after which a request is raised.
* It replaces the normally scattered calls to <i>notify()</i>. To be
* concretized by sub-aspects.
*/
protected abstract pointcut eventTrigger(Handler handler, Object request);
/**
* Call receiveRequest after a request was triggered.
*
* @param s the subject on which the change occured
*/
after(Handler handler, Object request): eventTrigger(handler, request) {
receiveRequest(handler, request);
}
/**
* Adds a successor to a handler.
*
* @param handler the handler to attach a new successor to
* @param successor the new successor to attach
*/
public void setSuccessor(Handler handler, Handler successor) {
successors.put(handler, successor);
}
/**
* Returns the successor of a handler.
*
* @param handler the handler in question
* @return the successor of the handler
*/
public Handler getSuccessor(Handler handler) {
return ((Handler) successors.get(handler));
}
/**
* Turns the notification mode on or off.
*
* @param choice true to turn notifications on, false to turn them off
*/
public void setNotification(boolean choice) {
this.notificationOn = choice;
}
/**
* Returns the successor of a handler.
*
* @param msg the message to print
*/
public void note(String msg) {
if (notificationOn) {
System.out.println(msg);
}
}
}</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZCommand.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.patterns.
*
* Contributor(s):
*/
/**
* This interface is implemented by <i>Command</i> objects.
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.0, 05/13/02
*
* @see Button
* @see Label
*/
public interface Command {
/**
* Executes the command.
*
* @param receiver the object this command is manipulating.
*/
public void executeCommand(CommandReceiver receiver);
/**
* Queries the command's executable status. This interface method is
* optional (default: all commands are excutable); a default
* implementation is provided by the abstract CommandProtocol aspect.
*
* @returns a boolean indicating whether the command is excutable.
*/
public boolean isExecutable();
}
</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZCommandInvoker.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.patterns.
*
* Contributor(s):
*/
/**
* This interface is used by extending aspects to say what types
* can be Invokers (i.e. senders of an executeCommand() call).
* This role is assigned by concrete sub-aspects of the <code>CommandProtocol
* </code> pattern aspect.
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.1, 10/29/02
*
* @see CommandProtocol
*/
public interface CommandInvoker { } </TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZMediatorProtocol.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.patterns.
*
* Contributor(s):
*/
import java.util.WeakHashMap;
import java.util.Collection;
import java.util.LinkedList;
import java.util.Iterator;
/**
* Defines the general behavior of the mediator design pattern.
*
* Each concrete sub-aspect of MediatorProtocol defines one kind of mediation
* relationship. Within that kind of relationship, there can be any number
* of <i>Colleague</i>s.
*
* The sub-aspect defines three things: <ol>
*
* <li> what types can be colleagues and mediator <br>
* this is done using +implements
*
* <li> what operations on the colleague require notifying the mediator<br>
* this is done by concretizing the change(Colleague) pointcut
*
* <li> how to update the observers <br>
* this is done by defining a method on
* updateObserver(Subject, Observer)
* </ol>
*
* Note that in this implementation, the work of updating is a method
* on the sub-aspect, not a method introduced on the observer. This
* allows one class of object to be the observer in different kinds of
* observing relationships, each of which has a different updating
* behavior. For observers that just have a single generic update
* behavior, the method on updateObserver will just be a simple call
* that generic updater.
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.0, 05/13/02
*
*/
public abstract aspect MediatorProtocol {
/**
* Assings the <code>Subject</code> role to the <code>Point</code> class.
* Roles are modeled as (empty) interfaces.
*/
protected interface Colleague { }
/**
* Assings the <code>Subject</code> role to the <code>Point</code> class.
* Roles are modeled as (empty) interfaces.
*/
protected interface Mediator { }
/**
* Stores the mapping between <code>Colleagues</code>s and <code>
* Mediator</code>s. For each colleague, its <code>Mediator</code>
* is stored.
*/
private WeakHashMap mappingColleagueToMediator = new WeakHashMap();
/**
* Returns the <code>Mediator</code> of
* a particular colleague. Used internally.
*
* @param colleague the colleague for which to return the mediator
* @return the <code>Mediator</code> of the colleague
*/
private Mediator getMediator(Colleague colleague) {
Mediator mediator =
(Mediator) mappingColleagueToMediator.get(colleague);
return mediator;
}
/**
* Sets the mediator for a colleague. This is a method on the pattern
* aspect, not the subject.
*
* @param colleague the colleague to set a new mediator for
* @param mediator the new mediator to set
*/
public void setMediator(Colleague c, Mediator m) {
mappingColleagueToMediator.put(c, m);
}
/**
* Defines what changes on Colleagues cause their mediator to be notified
*
* @param cs the colleague on which the change occured
*/
protected abstract pointcut change(Colleague c);
/**
* Call updateObserver to update each observer.
*/
after(Colleague c): change(c) {
notifyMediator(c, getMediator(c));
}
/**
* Defines how the <code>Mediator</code> is to be updated when a change
* to a <code>Colleague</code> occurs. To be concretized by sub-aspects.
*
* @param c the colleague on which a change of interest occured
* @param m the mediator to be notifed of the change
*/
protected abstract void notifyMediator(Colleague c, Mediator m);
}
</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZMemento.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
public interface Memento { // public to provide type to clients. public is not nice for methods, but we want to enforce all mementos to have those methods
public void setState(Object state);
public Object getState();
}
</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZMementoException.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.patterns.
*
* Contributor(s):
*/
/**
* Implements an exception that occurs if an incorrect originator is used
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.0, 07/13/02
*
* @see MementoProtocol
*/
public class MementoException extends RuntimeException {
/**
* Creates a MementoException
*
* @param s the error message
*/
public MementoException(String s) {
super(s);
}
}</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZMementoProtocol.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.patterns.
*
* Contributor(s):
*/
/**
* Implements the abstract memento design pattern. It defines the role of
* <i>Originator</i>. The <i>Memento</i> role is client-usable and as such
* defines outside this aspect.
*
* Concrete sub-aspects overwrite the two abstract methods to define how
* <i>Memento</i>s get generated and how they are used to restore the state
* of <i>Originator</i>s.
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.0, 07/13/02
*
*/
public abstract aspect MementoProtocol {
/**
* Defines the <i>Originator</i> type. Used only by pattern code
*/
protected interface Originator {}
/**
* Creates a <i>Memento</i> object for an <i>Originator</i>
*
* @param o the originator to create a memento for
* @returns the memento storing the originator's state
*/
public abstract Memento createMementoFor(Originator o);
/**
* Restores this originator to former state using the memento passed
*
* @param o the originator to restore
* @param m the memento that stores the prior state
*/
public abstract void setMemento(Originator o, Memento m);
}</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZObserverProtocol.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.patterns.
*
* Contributor(s):
*/
import java.util.WeakHashMap;
import java.util.List;
import java.util.LinkedList;
import java.util.Iterator;
/**
* Defines the general behavior of the observer design pattern.
*
* Each concrete sub-aspect of ObserverProtocol defines one kind of observing
* relationship. Within that kind of relationship, there can be any number
* of subjects, each with any number of observers.
*
* The sub-aspect defines three things: <ol>
*
* <li> what types can be subjects or observers <br>
* this is done using +implements
*
* <li> what operations on the subject require updating the observers <br>
* this is done by concretizing the changes(Subject) pointcut
*
* <li> how to update the observers <br>
* this is done by defining a method on
* updateObserver(Subject, Observer)
* </ol>
*
* Note that in this implementation, the work of updating is a method
* on the sub-aspect, not a method introduced on the observer. This
* allows one class of object to be the observer in different kinds of
* observing relationships, each of which has a different updating
* behavior. For observers that just have a single generic update
* behavior, the method on updateObserver will just be a simple call
* that generic updater.
*
* @author Gregor Kiczales
* @author Jan Hannemann
* @version 1.0, 05/13/02
*
*/
public abstract aspect ObserverProtocol {
/**
* This interface is used by extending aspects to say what types
* can be subjects. It models the subject role.
*/
protected interface Subject { }
/**
* This interface is used by extending aspects to say what types
* can be observers. It models the observer role.
*/
protected interface Observer { }
/**
* Stores the mapping between <code>Subject</code>s and <code>
* Observer</code>s. For each subject, a <code>LinkedList</code>
* is of its observers is stored.
*/
private WeakHashMap perSubjectObservers;
/**
* Returns a <code>Collection</code> of the observers of
* a particular subject. Used internally.
*
* @param s the subject for which to return the observers
* @return a <code>Collection</code> of s's observers
*/
protected List getObservers(Subject s) {
if (perSubjectObservers == null) {
perSubjectObservers = new WeakHashMap();
}
List observers = (List)perSubjectObservers.get(s);
if ( observers == null ) {
observers = new LinkedList();
perSubjectObservers.put(s, observers);
}
return observers;
}
/**
* Adds an observer to a subject. This is the equivalent of <i>
* attach()</i>, but is a method on the pattern aspect, not the subject.
*
* @param s the subject to attach a new observer to
* @param o the new observer to attach
*/
public void addObserver(Subject s, Observer o) {
getObservers(s).add(o);
}
/**
* Removes an observer from a subject. This is the equivalent of <i>
* detach()</i>, but is a method on the pattern aspect, not the subject.
*
* @param s the subject to remove the observer from
* @param o the observer to remove
*/
public void removeObserver(Subject s, Observer o) {
getObservers(s).remove(o);
}
/**
* The join points after which to do the update.
* It replaces the normally scattered calls to <i>notify()</i>. To be
* concretized by sub-aspects.
*/
protected abstract pointcut subjectChange(Subject s);
/**
* Call updateObserver after a change of interest to update each observer.
*
* @param s the subject on which the change occured
*/
after(Subject s): subjectChange(s) {
Iterator iter = getObservers(s).iterator();
while ( iter.hasNext() ) {
updateObserver(s, ((Observer)iter.next()));
}
}
/**
* Defines how each <code>Observer</code> is to be updated when a change
* to a <code>Subject</code> occurs. To be concretized by sub-aspects.
*
* @param s the subject on which a change of interest occured
* @param o the observer to be notifed of the change
*/
protected abstract void updateObserver(Subject s, Observer o);
}
</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZPrototypeProtocol.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.pattern.
*
* Contributor(s):
*/
/**
* Implements the abstract Prototype design pattern. It attaches a default
* <code>clone()</code> method on all <i>Prototype</i> participants and
* provides a static <code>cloneObject(Prototype)</clone> method. The default
* implementation of that method is to try to use the <code>clone()</code>
* method and, failing that, to call its protected <code>
* createCloneFor(Prototype)</code> method. Concrete subaspects can either
* overwrite none or one (or both) of the methods to create individual
* results
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.0, 05/13/02
*/
public abstract aspect PrototypeProtocol {
/**
* Defines the <i>Prototype</i> role.
*/
protected interface Prototype {}
/**
* Attaches a default <code>clone()</code> method to all prototypes.
* This makes use of Java's clone() mechanism that creates a deep copy
* of the object in question.
*
* @returns a copy of the object
*/
public Object Prototype.clone() throws CloneNotSupportedException {
return super.clone();
}
/**
* Provides a static default method for cloning prototypes.
* It uses the attached clone() method if possible. If not, it call the
* static <code>createCloneFor(Prototype)</code> method.
*
* @param object the prototype object to clone
* @returns a copy of the object
*/
public Object cloneObject(Prototype object) { // More Complex, allows to define what to do if superclass does not support clone
try {
return object.clone();
} catch (CloneNotSupportedException ex) {
return createCloneFor(object);
}
}
/**
* Provides an alternative method for cases when the default
* <code>clone()</code> method fails.
*
* @param object the prototype object to clone
* @returns a copy of the object
*/
protected Object createCloneFor(Prototype object) {
return null;
}
}</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZProxyProtocol.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.patterns.
*
* Contributor(s):
*/
import org.aspectj.lang.JoinPoint;
/**
* Defines the abstracted Proxy design pattern.<p>
*
* Concrete sub-aspects define the following: <UL>
* <LI> Which class(es) are subjects
* <LI> Which accesses should be protected (methods, field accesses)
* <LI> What alternative value should be returned in case of a denied
* access to a method.
* </UL>
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.0, 05/13/02
*
*/
public abstract aspect ProxyProtocol {
/**
* Defines the Subject role (for correct typing)
*/
protected interface Subject {}
/**
* Captures all accesses to the subject that should be protected by
* this pattern instance.
*/
protected abstract pointcut protectedAccess();
/**
* Extends the <code> protectedAccess()</code> pointcut to include a
* field for the joinpoint. Used internally only.
*/
private pointcut accessByCaller(Object caller):
protectedAccess() && this(caller);
/**
* Intercepts accesses to protected parts of the Subject. If access is
* rejected, the method <code>handleFailedAccess(..)</code> is called
* instead.
*
* @param caller the object responsible for the protected access
* @param subject the subject receiving the call
*/
Object around(Object caller, Subject subject):
accessByCaller(caller) && target(subject) {
if (! rejection(caller, subject, thisJoinPoint) )
return proceed(caller, subject);
return handleFailedAccess(caller, subject, thisJoinPoint);
}
/**
* Checks whether the access should be denied or not
*
* @param caller the object responsible for the protected access
* @param subject the subject receiving the call
* @param joinPoint the joinpoint associated with the protected access
*
* @returns true if the access is denied, false otherwise
*/
protected abstract boolean rejection(Object caller,
Subject subject,
JoinPoint joinPoint);
/**
* For delegation: Provides an alternative return value if access
* is denied.
*
* @param caller the object responsible for the protected access
* @param subject the subject receiving the call
* @param joinPoint the joinpoint associated with the protected access
*
* @returns an alternative return value
*/
protected abstract Object handleFailedAccess(Object caller,
Subject subject,
JoinPoint joinPoint);
}
</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZSingletonProtocol.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.patterns.
*
* Contributor(s):
*/
import java.util.Hashtable;
/**
* Defines the general behavior of the singleton design pattern.
*
* Each concrete sub-aspect of SingletonProtocol defines the Singleton
* property for one class.
*
* The sub-aspect defines two things: <ol>
*
* <li> what type is a <i>Singleton</i> <br>
*
* <li> what classes can access the <i>Singleton</i>'s constructor (if any)
* despite its property
* </ol>
*
* for this implementation we choose to illustrate that it is not necessary
* to provide a factory method for (like getSingleton()), but the regular
* constructor may be used instead to access the Singleton instance
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.0, 05/13/02
*
*/
public abstract aspect SingletonProtocol {
private Hashtable singletons = new Hashtable();
public interface Singleton {}
protected pointcut protectionExclusions(); // What if two aspects re-define protectionExclusions() ?
Singleton around(): call((Singleton+).new(..)) && !protectionExclusions() {
Class singleton = thisJoinPoint.getSignature().getDeclaringType();
if (singletons.get(singleton) == null) { // How to access the static instance variable here?
singletons.put(singleton, proceed());
}
return (Singleton) singletons.get(singleton);
}
// Alternative to protectionExclusions() ?:
//
// Define an interface NonSingleton and check in advice whether
// we are asked to create a NonSingleton, then proceed
}</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZStrategyProtocol.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.patterns.
*
* Contributor(s):
*/
import java.util.Hashtable;
/**
* Implements the the abstract strategy design pattern protocol<p>
*
* Intent: <i>Define a family of algorithms, encapsulate each one, and make
* them interchangeable. Strategy lets the algorithm vary independently from
* clients that use it.</i><p>
*
* Participatng objects are <code>LinearSort</code> and <i>BubbleSort</i>
* as <i>Strategies</i>, and <code>Sorter</code> as <i>Context</i>.
*
* In this example, an array of 10 numbers is to be sorted. Depending on the
* number of arguments of the call to <code>Main</code>, linear sort or
* bubblesort are used as sorting algorithms.
*
* <p><i>This is the AspectJ version.</i><p>
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.0, 05/13/02
*
* @see LinearSort
* @see BubbleSort
*/
public abstract aspect StrategyProtocol {
/**
* Stores the current strategy for each context
*
* @param numbers the int array to sort
*/
Hashtable strategyPerContext = new Hashtable();
/**
* Defines the <i>Strategy</i> role
*/
protected interface Strategy { }
/**
* Defines the <i>Context</i> role
*/
protected interface Context { }
/**
* Attaches a strategy field to each context
*/
private Strategy Context.strategy = null;
/**
* Sets the strategy for a given context
*
* @param c the context to set the strategy for
* @param s the new strategy
*/
public void setConcreteStrategy(Context c, Strategy s) { strategyPerContext.put(c, s); }
/**
* Returns the strategy for a given context
*
* @param c the context object
* @returns the strategy object for that context
*/
public Strategy getConcreteStrategy(Context c) { return (Strategy) strategyPerContext.get(c); }
}
// abstract pointcut useStrategy(Context c);
// abstract pointcut setStrategy(Context c, Strategy s);
// before(Context c): useStrategy(c) {
// c.strategy = getConcreteStrategy(c);
// }
// after(Context c, Strategy s): setStrategy(c, s) {
// setConcreteStrategy(c, s);
// }
// idea: have aspect define method useStrategy() ?
</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00ZVisitorProtocol.java2004-03-24T16:00:00Z2004-03-24T16:00:00Z<br/><TEXTAREA name="code" class="java" rows="16" cols="100">package ca.ubc.cs.spl.pattern.library;
/* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
*
* This file is part of the design patterns project at UBC
*
* The contents of this file are subject to the Mozilla Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* either http:*www.mozilla.org/MPL/ or http:*aspectj.org/MPL/.
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is ca.ubc.cs.spl.pattern.
*
* Contributor(s):
*/
/**
* Implements the abstracted Visitor design pattern.<p>
*
* Intent: <i>Represents an operation to be performed on the elements of an
* object structure. Visitor lets you define a new operation without changing
* the classes of the elements on which it operates</i><p>
*
* This code defines the roles <code>VisitorNode</code>, <code>VRegularNode
* </code>, and <code>VLeaf</code>, representing a general node interface,
* a non-terminal binary tree node, and a terminal node, respectively.
* This aspect attaches default implementations of the various
* <code>accept(..)</code> methods to the (abstract) participants. Concrete
* subaspects just have to assign roles. Concrete Visitors implement the
* inner interface <code>NodeVisitor</code>. <p>
*
* Note that this implementation only deals with two different kind of nodes:
* terminal and non-terminal nodes. In cases where the aggregate structure
* contains more types of nodes, this aspect cannot be used without
* modifications. <p>
*
* Note further that whenever the aggregate structure is unimportant, the
* additional functionality can be added using AspectJ's open classes
* mechanism, i.e. by simply attaching the new methods to existing classes.
*
* @author Jan Hannemann
* @author Gregor Kiczales
* @version 1.0, 06/13/02
*/
public abstract aspect VisitorProtocol {
/**
* Defines the <i>Element</i> role. The inerface is public so that
* concrete visitors can use the type.
*/
public interface VisitorNode {}
/**
* Defines a <i>ConcreteElement</i> role for non-terminal nodes in
* a binary tree structure. The inerface is protected as it is only used
* bu concrete subaspects.
*/
protected interface VRegularNode extends VisitorNode {}
/**
* Defines a <i>ConcreteElement</i> role for terminal nodes in
* a tree structure. The inerface is protected as it is only used
* bu concrete subaspects.
*/
protected interface VLeaf extends VisitorNode {}
/**
* This inerface is implemented by <i>ConcreteVisitor</i>s.
*/
public interface NodeVisitor {
/**
* Defines a method signature for visiting regular nodes.
*
* @param node the regular node to visit
*/
public void visitRegularNode(VisitorNode node);
/**
* Defines a method signature for visiting leaf nodes.
*
* @param node the leaf node to visit
*/
public void visitLeaf(VisitorNode node);
/**
* Defines a method signature for returning the visitor's results
*
* @param node a string containig the visitor's results
*/
public String report();
}
/**
* Attaches the <code>accept(..)</code> code to nodes
*
* @param nv the visitor that is to be accepted
*/
public void VisitorNode.accept(NodeVisitor nv) {}
/**
* Attaches the <code>accept(..)</code> code to regular nodes
*
* @param nv the visitor that is to be accepted
*/
public void VRegularNode.accept(NodeVisitor nv) {
nv.visitRegularNode(this);
}
/**
* Attaches the <code>accept(..)</code> code to leaf nodes
*
* @param nv the visitor that is to be accepted
*/
public void VLeaf.accept(NodeVisitor nv) {
nv.visitLeaf(this);
}
}</TEXTAREA><br><br/><script type="text/javascript"><!--google_ad_client = "pub-9426659565807829";google_ad_slot = "9359905831";google_ad_width = 728;google_ad_height = 15;//--></script><script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>2004-03-24T16:00:00Z