You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@river.apache.org by si...@apache.org on 2010/12/24 20:54:07 UTC

svn commit: r1052569 [13/17] - in /incubator/river/site/trunk/content/river/doc/specs/html: ./ images/

Added: incubator/river/site/trunk/content/river/doc/specs/html/lrs-spec.html
URL: http://svn.apache.org/viewvc/incubator/river/site/trunk/content/river/doc/specs/html/lrs-spec.html?rev=1052569&view=auto
==============================================================================
--- incubator/river/site/trunk/content/river/doc/specs/html/lrs-spec.html (added)
+++ incubator/river/site/trunk/content/river/doc/specs/html/lrs-spec.html Fri Dec 24 19:54:05 2010
@@ -0,0 +1,496 @@
+<!--
+ ! Licensed to the Apache Software Foundation (ASF) under one
+ ! or more contributor license agreements.  See the NOTICE file
+ ! distributed with this work for additional information
+ ! regarding copyright ownership. The ASF licenses this file
+ ! to you under the Apache License, Version 2.0 (the
+ ! "License"); you may not use this file except in compliance
+ ! with the License. You may obtain a copy of the License at
+ ! 
+ !      http://www.apache.org/licenses/LICENSE-2.0
+ ! 
+ ! Unless required by applicable law or agreed to in writing, software
+ ! distributed under the License is distributed on an "AS IS" BASIS,
+ ! WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ! See the License for the specific language governing permissions and
+ ! limitations under the License.
+ !-->
+
+<html>
+
+<head>
+<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
+<meta name="GENERATOR" content="Quadralay WebWorks Publisher 5.0.4">
+<link rel="StyleSheet" href="standard.css" type="text/css" media="screen">
+<title>Jini Lease Renewal Service Specification  </title>
+</head>
+
+<body bgcolor="#ffffff">
+
+
+<a href="#skip" title="Skip navigation bar"></a>
+<table width="100%">
+<tr>
+<td align=left><a href="../../spec-index.html">Spec Index</a></td>
+<td align=right><em>A Collection of Jini Technology Helper Utilities and Services Specifications</em></td>
+</tr>
+</table>
+<br clear="all">
+
+
+<hr align="left">
+<table width="90%">
+<tr>
+<td align="right" font size="4"><b>Version 1.0</b></td>
+</tr>
+</table>
+<a name="skip"></a>
+<blockquote>
+<h2>
+  <a name="1005695"> </a>LR - Jini<font size="-1"><sup>TM</sup></font> Lease Renewal Service Specification
+</h2>
+<h3 class="Heading2">
+  <a name="1000045"> </a>LR.1	 Introduction
+</h3>
+<p class="Body">
+  <a name="1006066"> </a>Leasing is a key concept in the Jini<font size="-1"><sup>TM</sup></font> architecture; in general, Jini technology-enabled services (<em class="Emphasis">Jini services</em>) grant access to a resource only for as long as the clients of those Jini services actively express interest in the resource being maintained. This pattern is in contrast to many other systems, in which access to a resource is granted until the client explicitly releases the resource. Using a leasing model generally makes a distributed system more robust by allowing stale information and services to be cleaned up, but it also places additional requirements on clients and services.
+</p>
+<p class="Body">
+  <a name="1001371"> </a>A client of a leased service may run into difficulties if that client deactivates. Unless the client ensures that some other process renews the client's leases while it is inactive, or that the client is activated before its leases begin to expire, the client will lose access to the resources it has acquired. This loss can be particularly dramatic in the case of lookup service registrations. A service's registration with a lookup service is leased--if the service deactivates (maybe to conserve computational resources on its host) and it does not take appropriate steps, its registrations with lookup services will expire, and before long it will be inaccessible. If that service becomes active only when clients invoke its methods, it may never become active again, because at this point new clients may not be able to find it.
+</p>
+<p class="Body">
+  <a name="1006118"> </a>The need to renew leases creates a constant load on clients, servers, and the network. Although batching lease renewals can help (see the <a href="lease-spec.html"><em class="Emphasis">Jini Distributed Leasing Specification</em></a>), a given client is unlikely to have very many leases granted by any one service at any given time, thus reducing the opportunities for meaningful batching.
+</p>
+<p class="Body">
+  <a name="1002224"> </a>This additional load may be an especially great burden on clients that always have the ability to access the network but cannot be continuously connected. A cell phone always has the ability to connect; however, being connected all the time will drain its batteries and accumulate airtime charges. One or two leases may not pose a problem, but a large number of leases could force the phone to be on the network all the time.
+</p>
+<p class="Body">
+  <a name="1002237"> </a>A lease renewal service can help mitigate these problems. Clients that wish to become inactive can pass the responsibility for renewing the leases they have been granted to a renewal service. Those clients can then deactivate without risk of losing access to the resources that they have acquired. Clients that have continuous access to the network but cannot be continuously connected, such as the cell phone described previously, can also register with a renewal service that can be continuously connected. The renewal service will renew the client's leases, allowing the client to remain disconnected most of the time. Lastly, if multiple clients pass their leases to a given renewal service, more opportunities for batching renewals will be created.
+</p>
+<p class="Body">
+  <a name="1000205"> </a>Like other Jini services, the lease renewal service will grant its services for only a limited period of time without an active expression of continuing interest. To break the recursive cycle that would otherwise result, the renewal service provides an optional event that is triggered before the leases that it grants expire. This event gives activatable processes that have deactivated the opportunity to wake up and renew their lease with the renewal service. Although it may seem odd for the lease renewal service to lease its resources, it is very important that it does so. If it did not, then the lease renewal service could be used to subvert the leasing model.
+</p>
+<p class="Body">
+  <a name="1010114"> </a>Lease renewal services are likely to grant longer leases than other Jini services. In some cases the lease may be so long that the client will not need to worry about renewing the lease at all. In other cases the lease may be long enough that a client that deactivates will rarely need to reactivate for the sole purpose of renewing its lease with the renewal service. In any case, the leases that the renewal service grants are likely to be sufficiently long such that the actual renewal calls do not place a significant additional load on the client, the renewal service, or the network.
+</p>
+<h4 class="Heading3">
+  <a name="1000297"> </a>LR.1.1	  Goals and Requirements 
+</h4>
+<p class="Body">
+  <a name="1000304"> </a>The requirements of the set of classes and interfaces in this specification are:
+</p>
+<ul>
+
+  <li class="SmartList1"><a name="1000305"> </a>To provide a service for renewing leases<p>
+  <li class="SmartList1"><a name="1000307"> </a>To provide this service in such a way that it can be used by activatable processes that deactivate<p>
+  <li class="SmartList1"><a name="1000312"> </a>To provide this service in a way that does not overly weaken the leasing model
+</ul>
+
+<p class="Body">
+  <a name="1000323"> </a>The goals of this specification are:
+</p>
+<ul>
+
+  <li class="SmartList1"><a name="1000359"> </a>To describe the lease renewal service<p>
+  <li class="SmartList1"><a name="1000360"> </a>To provide guidance in the use, deployment, and implementation of the lease renewal service
+</ul>
+
+<h4 class="Heading3">
+  <a name="1000361"> </a>LR.1.2	 Other Types
+</h4>
+<p class="Body">
+  <a name="1006404"> </a>The types defined in the specification of the <code>LeaseRenewalService</code> interface are in the <code>net.jini.lease</code> package. The following object types may be referenced in this chapter. Whenever referenced, these object types will be referenced in unqualified form:
+</p>
+<pre  class="Preformatted">
+java.io.IOException
+java.rmi.MarshalledObject
+java.rmi.RemoteException
+java.rmi.NoSuchObjectException
+net.jini.core.lease.Lease
+net.jini.core.lease.UnknownLeaseException
+net.jini.core.event.RemoteEvent
+net.jini.core.event.RemoteEventListener
+net.jini.core.event.EventRegistration
+</pre>
+<h3 class="Heading2">
+  <a name="1001235"> </a>LR.2	 The Interface
+</h3>
+<p class="Body">
+  <a name="1011893"> </a>The <code>LeaseRenewalService</code> (in the <code>net.jini.lease</code> package) defines the interface to the renewal service. The interface is not a remote interface; each implementation of the renewal service exports proxy objects that implement the <code>LeaseRenewalService</code> interface local to the client, using an implementation-specific protocol to communicate with the actual remote server. All of the proxy methods obey normal Java(TM) Remote Method Invocation (Java RMI) remote interface semantics. Two proxy objects are equal (using the <code>equals</code> method) if they are proxies for the same renewal service. All the methods of <code>LeaseRenewalService</code> throw <code>RemoteException</code> and require only the default serialization semantics. Therefore, <code>LeaseRenewalService</code> can be implemented directly using Java RMI.
+</p>
+<pre  class="Preformatted">
+package net.jini.lease;
+
+public interface LeaseRenewalService {
+    public LeaseRenewalSet createLeaseRenewalSet(
+            long leaseDuration) 
+        throws RemoteException;
+}
+</pre>
+<p class="Body">
+  <a name="1000478"> </a>Clients of the renewal service organize the leases they wish to have renewed into <em class="Emphasis">lease renewal sets</em> (or <em class="Emphasis">sets,</em> for short). A method is provided by the <code>LeaseRenewalService</code> interface to create these sets. These sets are then populated by methods on the sets themselves. Two leases in the same set need not be granted by the same service or have the same expiration time; in addition, they can be added or removed from the set independently.
+</p>
+<p class="Body">
+  <a name="1010728"> </a>Every method invocation on a renewal service (whether the invocation is directly on the service or indirectly on a <code>set</code> the service has created) is atomic with respect other invocations.
+</p>
+<p class="Body">
+  <a name="1006811"> </a>The term <em class="Emphasis">client lease</em> is used to refer to a lease that has been placed into a renewal set. Client leases are distinct from the leases that the renewal service grants on renewal sets it has created.
+</p>
+<p class="Body">
+  <a name="1011925"> </a>In general, there will be times when an implementation of the renewal service needs to pass one client lease as an argument to a method call on a second client lease. There is a security risk in doing so, because such actions can let the second client lease "capture" the first.Implementations may want to verify that their clients can be trusted not to place leases in the set that would take such actions, or may choose to avoid passing client leases to each other if the leases are contained in different sets.</p>
+<p class="Body">
+  <a name="1010566"> </a>Each client lease has two expiration related times associated with it: the <em class="Emphasis">desired expiration</em> time for the lease and the <em class="Emphasis">actual expiration</em> time granted when the lease is created or last renewed. The desired expiration represents when the client would like the lease to expire. The actual expiration represents when the lease is going to expire if it is not renewed. Both time values are absolute times, not relative time durations. When a client lease's desired expiration arrives, the lease will be removed from the set without further client intervention. 
+</p>
+<p class="Body">
+  <a name="1011315"> </a>Each client lease also has two other associated attributes: a <em class="Emphasis">renewal duration </em>and a <em class="Emphasis">remaining desired duration</em>. The remaining desired duration is always the desired expiration less the current time. The renewal duration is usually a positive number and represents the duration that will be requested when the renewal service renews the client lease, unless the renewal duration is greater than the remaining desired duration. If the renewal duration is greater than the remaining desired duration, then the remaining desired duration will be requested when renewing the client lease. One exception is that when the desired expiration is <code>Lease.FOREVER</code>, the renewal duration may be <code>Lease.ANY</code>, in which case <code>Lease.ANY</code> will be requested when renewing the client lease, regardless of the value of the remaining desired duration.
+</p>
+<p class="Body">
+  <a name="1011325"> </a>For example, if the renewal duration associated with a given client lease is 360,000 milliseconds, then when the renewal service renews the client lease, it will ask for a new duration of 360,000 milliseconds--unless the client lease is going to reach its desired expiration in less than 360,000 milliseconds. If the client lease's desired expiration is within 360,000 milliseconds, the renewal service will ask for the difference between the current time and the desired expiration. If the renewal duration had been <code>Lease.ANY</code>, the renewal service would have asked for a new duration of <code>Lease.ANY</code>.
+</p>
+<p class="Body">
+  <a name="1011239"> </a>If a lease's actual expiration is later than the lease's desired expiration, the renewal service will not renew the lease; the lease will remain in the set until its desired expiration is reached, the set is destroyed, or it is removed by the client.
+</p>
+<p class="Body">
+  <a name="1011330"> </a>Each set is leased from the renewal service. If the lease on a set expires or is cancelled, the renewal service will destroy the set and take no further action with regard to the client leases in the set. Each lease renewal set has associated with it an expiration warning event that occurs at a client-specified time before the lease <em class="Emphasis">on the set</em> expires. Clients can register for warning events using methods provided by the set. A registration for warning events does not have its own lease, but instead is covered by the same lease under which the set was granted.
+</p>
+<p class="Body">
+  <a name="1011735"> </a>The term <em>definite exception</em> is used to refer to an exception that could be thrown by an operation (such as a remote method call) on an object, for example a client lease, that would be indicative of a permanent failure of that object. The term <em>indefinite exception</em> refers to exceptions that would not imply anything about the probability of success of any future operations on the object. The algorithm used to classify exceptions as definite or indefinite is implementation-specific.</p>
+<p class="Body">
+  <a name="1011736"> </a>Each lease renewal set has associated with it a renewal failure event that will occur in either of two cases: if any client lease in the set reaches its actual expiration before its desired expiration is reached, or if the renewal service attempts to renew a client lease and gets a definite exception. Clients can register for failure events using methods provided by the set. A registration for failure events does not have its own lease but instead is covered by the same lease under which the set was granted.
+</p>
+<p class="Body">
+  <a name="1012324"> </a>Once placed in a set, a client lease will stay there until one or more of the following occurs:
+</p>
+<ul>
+
+  <li class="SmartList1"><a name="1012321"> </a>The lease on the set itself expires or is cancelled, causing destruction of the set.<p>
+  <li class="SmartList1"><a name="1000503"> </a>The client lease is removed by the client.<p>
+  <li class="SmartList1"><a name="1011141"> </a>The client lease's desired expiration is reached.<p>
+  <li class="SmartList1"><a name="1011142"> </a>The client lease's actual expiration is reached; this will generate a renewal failure event.<p>
+  <li class="SmartList1"><a name="1011143"> </a>A renewal attempt on the client lease results in a definite exception; this will generate a renewal failure event.
+</ul>
+
+<p class="Body">
+  <a name="1000514"> </a>Each client lease in a set will be renewed as long as it is in the set. If a renewal call throws an indefinite exception, the renewal service should retry the lease renewal until the lease would otherwise be removed from the set. The preferred method of cancelling a client lease is for the client to first remove the lease from the set and then call <code>cancel</code> on it. It is also permissible for the client to cancel the lease without first removing the lease from the set, although this is likely to result in additional network traffic.
+</p>
+<p class="Body">
+  <a name="1000593"> </a>The client creates a set by calling the <code>createLeaseRenewalSet</code> method of a <code>LeaseRenewalService</code>. The <code>leaseDuration</code> argument specifies how long (in milliseconds) the client wants the set's initial lease duration to be. The duration initially granted for the set's lease will be equal to or shorter than this request; it will not be longer. The value of the <code>leaseDuration</code> argument must be positive, <code>Lease.FOREVER</code>, or <code>Lease.ANY</code>; otherwise, an <code>IllegalArgumentException</code> will be thrown. Two calls to the <code>createLeaseRenewalSet</code> method will never return objects that are equal. The set's lease is obtained through a method provided by the set.
+</p>
+<p class="Body">
+  <a name="1000634"> </a><code>LeaseRenewalSet</code> defines the interface to the sets created by the lease renewal service. This interface is not a remote interface. Each implementation of the renewal service exports proxy objects that implement the <code>LeaseRenewalSet</code> interface local to the client and use an implementation-specific protocol to communicate with the actual remote server. All of the proxy methods obey normal Java RMI remote interface semantics except where explicitly noted. The proxy objects for two sets are equal (using the <code>equals</code> method) if they are proxies for the same set created by the same renewal service. Any method that communicates with the remote server should throw a <code>NoSuchObjectException</code> if the set no longer exists. If a client receives a <code>NoSuchObjectException</code> from one of the operations on a lease renewal set, the client can infer that the set has been destroyed; however, it should <em class="Emphas
 is">not</em> infer that the renewal service has been destroyed.
+</p>
+<pre  class="Preformatted">
+package net.jini.lease;
+
+public interface LeaseRenewalSet {
+    final public static long RENEWAL_FAILURE_EVENT_ID = 0;
+    final public static long EXPIRATION_WARNING_EVENT_ID = 1;
+
+    public void renewFor(Lease leaseToRenew,
+                     long  desiredDuration,	 
+                     long  renewDuration)
+        throws RemoteException;
+
+    public void renewFor(Lease leaseToRenew, 
+                         long  desiredDuration)
+        throws RemoteException;
+    
+    public EventRegistration setExpirationWarningListener(
+            RemoteEventListener listener, 
+            long                minWarning, 
+            MarshalledObject    handback)
+        throws RemoteException;
+
+    public void clearExpirationWarningListener()
+        throws RemoteException;
+
+    public EventRegistration setRenewalFailureListener(
+            RemoteEventListener listener, 
+            MarshalledObject    handback)
+        throws RemoteException;
+
+    public void clearRenewalFailureListener()
+        throws RemoteException;
+
+    public Lease remove(Lease leaseToRemove) 
+        throws RemoteException;
+   
+    public Lease[] getLeases() 
+        throws LeaseUnmarshalException, RemoteException;
+
+    public Lease getRenewalSetLease();
+}
+</pre>
+<p class="Body">
+  <a name="1000636"> </a>Leases can be added to the set through the <code>renewFor</code> methods. There are two forms of this method: a three-argument form and a two-argument form. The three-argument form will be described first. The <code>leaseToRenew</code> argument specifies the lease to be renewed. An <code>IllegalArgumentException</code> will be thrown if the lease has not expired and was granted by the renewal service itself. If <code>leaseToRenew</code> is <code>null</code>, a <code>NullPointerException</code> will be thrown.
+</p>
+<p class="Body">
+  <a name="1002945"> </a>The <code>desiredDuration</code> parameter is the number of milliseconds that the client would like for the client lease to remain in the set. It is used to calculate the client lease's desired expiration by adding <code>desiredDuration</code> to the current time (as viewed by the service). If this causes an overflow, a desired expiration of <code>Long.MAX_VALUE</code> will be used. Unlike a lease duration, the desired duration is unilaterally specified by the client, not negotiated between the client and the service. Note that a negative value for <code>desiredDuration</code> (including <code>Lease.ANY</code>) will result in a desired expiration that is in the past. This will cause the client lease to be dropped immediately from the set and will not result in an exception. A renewal failure event will be generated if and only if the client's actual expiration is before its desired expiration.
+</p>
+<p class="Body">
+  <a name="1010620"> </a>If the actual expiration time of the client lease being added to the set is before both the current time (as viewed by the renewal service) and the client lease's desired expiration time, the method will return normally. However, the client lease will be dropped from the set, and a renewal failure event will be generated. If the actual expiration time is before the current time and equal to or after the desired expiration time, the method will return normally, the client lease will be dropped from the set, and no event will be generated.
+</p>
+<p class="Body">
+  <a name="1001980"> </a>A <code>desiredDuration</code> of <code>Long.MAX_VALUE</code> does not imply that the client lease will remain in the set forever. The client lease will be ejected from the set if the set is destroyed, the client lease itself expires, the client lease is removed from the set, or the renewal service makes a renewal attempt on the client lease that results in a definite exception.
+</p>
+<p class="Body">
+  <a name="1010388"> </a>The <code>renewDuration</code> is the renewal duration to associate with the client lease (in milliseconds). If <code>desiredDuration</code> is exactly <code>Long.MAX_VALUE</code>, the <code>renewDuration</code> may be any positive number or <code>Lease.ANY</code>; otherwise it must be a positive number. If these requirements are not met, the renewal service will throw an <code>IllegalArgumentException</code>.
+</p>
+<p class="Body">
+  <a name="1010386"> </a>Calling <code>renewFor</code> with a lease that is equivalent to a client lease already in the set will associate the existing client lease in the set with the new desired duration and renew duration. The original copy of the client lease is not replaced with the new one. These semantics also allow <code>renewFor</code> to be used in an idempotent fashion.
+</p>
+<p class="Body">
+  <a name="1010398"> </a>The two-argument form of <code>renewFor</code> is equivalent to
+</p>
+<pre  class="Preformatted">
+renewFor(leaseToRenew, desiredDuration, Lease.FOREVER)
+</code></pre>
+<p class="Body">
+  <a name="1011085"> </a>Client leases get returned to clients in a number of ways (via <code>remove</code> and <code>getLeases</code> calls, as components of events, etc.). The serial format of client leases returned to clients may be either <code>Lease.DURATION</code> or <code>Lease.ABSOLUTE</code>. In particular it may be necessary to use the <code>Lease.ABSOLUTE</code> format if the implementation has access to the client lease only in marshalled form and is unable to unmarshal the client lease before sending it to the client.
+</p>
+<p class="Body">
+  <a name="1011947"> </a>Whenever a client lease gets returned to a client, its actual expiration should reflect either:
+</p>
+<ul>
+
+  <li class="SmartList1"><a name="1011948"> </a>The result of the last recorded successful renewal of the client lease performed by the renewal service; or<p>
+  <li class="SmartList1"><a name="1010528"> </a>The expiration time the client lease originally had when it was added to the set, if the renewal service has been unable to successfully renew the client lease and record the result
+</ul>
+
+<p class="Body">
+  <a name="1006810"> </a>Although it is impossible for a renewal service to guarantee that all renewal attempts will be recorded, persistent implementations should attempt to keep the interval between the renewal of a client lease and the logging of the result to a minimum.
+</p>
+<p class="Body">
+  <a name="1011276"> </a>Client leases are removed from the set by using the <code>remove</code> method. Removal from the set will not cause the lease to be cancelled. The method will return the lease that is being removed. If the lease is not in the set, <code>null</code> will be returned; and this call will not be blocked by in-progress renewal attempts. As a result, a client lease removed by this method might be renewed after the method has returned. Implementations should keep the window where renewals of removed leases could occur as small as possible.
+</p>
+<p class="Body">
+  <a name="1007318"> </a>The <code>getLeases</code> method returns all the client leases in the set at the time of the call, as an array of type <code>Lease</code>. If one or more of the <code>Lease</code>s in the array cannot be deserialized, a <code>LeaseUnmarshalException</code> is thrown.
+</p>
+<pre  class="Preformatted">
+package net.jini.lease;
+
+public class LeaseUnmarshalException extends Exception {
+    public LeaseUnmarshalException(
+            Lease[]            leases,
+            MarshalledObject[] marshalledLeases,
+            Throwable[]        exceptions) {...}
+    public LeaseUnmarshalException(
+            Lease[]            leases,
+            MarshalledObject[] marshalledLeases,
+            Throwable[]        exceptions,
+            String             message) {...}
+
+    public Lease[] getLeases() {...}
+    public MarshalledObject[] getMarshalledLeases() {...}
+    public Throwable[] getExceptions() {...}
+}
+</pre>
+<p class="Body">
+  <a name="1006801"> </a>The leases that could be successfully deserialized will be returned by the <code>getLeases</code> method of the exception. If no leases could be deserialized, a zero-length array will be returned. The leases that could not be deserialized will be returned in the form of <code>MarshalledObject</code>s by the <code>getMarshalledLeases</code> method of the exception. For each element of the array returned by the <code>getMarshalledLeases</code> method, the corresponding element of the array returned by the <code>getExceptions</code> method will hold a <code>Throwable</code> that indicates why the given lease could not be deserialized.
+</p>
+<p class="Body">
+  <a name="1010402"> </a>Throwing a <code>LeaseUnmarshalException</code> represents a (possibly transient) failure in the ability to unmarshal one or more client leases in the set; it does not necessarily imply anything about the state of the renewal service or the set that threw the exception.
+</p>
+<p class="Body">
+  <a name="1006782"> </a>The <code>getRenewalSetLease</code> method of <code>LeaseSet</code> returns the lease associated with the set itself. This method does not make a remote call.
+</p>
+<h4 class="Heading3">
+  <a name="1006552"> </a>LR.2.1	 Events
+</h4>
+<p class="Body">
+  <a name="1006553"> </a>The lease renewal service does not support multiple simultaneous event listener registrations for the same kind of event. Although it would be useful in some limited circumstances, to do so would require event registrations to be leased separately from the set they are associated with. For the average client of the lease renewal service, this ability would increase the number of leases that it would have to manage. Since the renewal service is based on the premise that some clients have difficulty managing their own leases, increasing the number of leases that a client would need to manage could significantly complicate the implementation of those clients. Because there can be at most one listener for each kind of event, a given set provides a <code>set/clear</code> interface instead of the more common <code>addListener/removeListener</code> or <code>addListener/lease.cancel</code> interfaces.
+</p>
+<p class="Body">
+  <a name="1011984"> </a>The source field of each event generated by a lease renewal service is the renewal set that the event is associated with. In the case of an expiration warning event, this is the set that is about to expire. In the case of a renewal failure event, this is the set the client lease was in when the event occurred. Note that the value of the source field will in general be a copy of the set in question, the <code>equals</code> method will return <code>true</code> for any other copies of the set the client has in its possession, but in general it will not be the same object (that is, comparing two sets using <code>==</code> will usually return <code>false</code>).
+</p>
+<p class="Body">
+  <a name="1011985"> </a>The event ID <code>LeaseRenewalSet.EXPIRATION_WARNING_EVENT_ID</code> is used for all expiration warning events. One event ID is used because there is only one kind of expiration warning event. Similarly, all renewal failure events will have the event ID <code>LeaseRenewalSet.RENEWAL_FAILURE_EVENT_ID</code>.
+</p>
+<p class="Body">
+  <a name="1011679"> </a>Because all of the expiration warning events generated by a given set will have the same source and event ID, the sequence number of any given expiration warning event generated by the set will be different from the sequence number of any other expiration warning event generated by the set. Similarly, the sequence number of any renewal failure event generated by a given set will be different from the sequence number of any other renewal failure event generated by the set. Two different events with the same source and event ID will have different sequence numbers even if different event registration were in effect when each event was generated.
+</p>
+<p class="Body">
+  <a name="1007437"> </a>If a <code>RemoteEventListener</code> registered for a renewal failure or expiration warning event throws an <code>UnknownEventException</code>, this action will only clear the specific event registration. It will not cancel the lease on the renewal set or affect any other event registration on the set. If the listener throws a definite exception, the renewal service may clear that specific event registration; it will not clear any registration associated with other listeners, nor will it cancel the lease on the associated renewal set.
+</p>
+<p class="Body">
+  <a name="1006698"> </a>If an event listener is replaced and one or more event delivery attempts on the original listener failed, implementations may choose to send some or all of these events to the new listener.
+</p>
+<p class="Body">
+  <a name="1011713"> </a>Event listeners may receive notification of events that they are no longer registered to receive, if those events occurred before they were unregistered. Implementations should keep the window where such notifications could occur as small as possible.
+</p>
+<p class="Body">
+  <a name="1011714"> </a>The <code>setExpirationWarningListener</code> method of <code>LeaseRenewalSet</code> allows the client to register for notification of the approaching expiration of the <em class="Emphasis">set's </em>lease. Expiration warning events are not generated for client leases. The <code>listener</code> argument specifies which listener should be notified when the set's lease is about to expire. The <code>minWarning</code> argument specifies the minimum number of milliseconds before set lease expiration that the first event delivery attempt should be made by the service. The service may also make subsequent delivery attempts if the first and any subsequent attempts resulted in an indefinite exception. The <code>minWarning</code> argument must be zero or a positive number; if it is not, an <code>IllegalArgumentException</code> must be thrown. If the current expiration of the set's lease is less than <code>minWarning</code> milliseconds away, the event will oc
 cur immediately (though it will take time to propagate to the handler).
+</p>
+<p class="Body">
+  <a name="1002363"> </a>The <code>handback</code> argument to <code>setExpirationWarningListener</code> specifies an object that will be part of the expiration warning event notification. This mechanism is detailed in the <a href="event-spec.html"><em class="Emphasis">Jini Distributed Events Specification</em></a>.
+</p>
+<p class="Body">
+  <a name="1012046"> </a>The <code>setExpirationWarningListener</code> method returns the event registration for this event. The <code>Lease</code> object associated with the registration will be equivalent (in the sense of the <code>equals</code> method) to the <code>Lease</code> on the renewal set. Because the event registration shares a lease with the set, clients that want to just remove their expiration warning registration without destroying the set should use the <code>clearExpirationWarningListener</code> method described below, instead of cancelling the registration's lease. The event ID returned with the registration will be <code>LeaseRenewalSet.EXPIRATION_WARNING_EVENT_ID</code>. The source of the registration will be the set. The method will throw a <code>NullPointerException</code> if the <code>listener</code> argument is <code>null</code>. If an event handler has already been specified for this event, the current registration is replaced with the new one. Beca
 use both registrations are for the same kind of event, the events sent to the new registration must be in the same sequence as the events sent to the old registration.
+</p>
+<p class="Body">
+  <a name="1001577"> </a>The <code>clearExpirationWarningListener</code> method of <code>LeaseRenewalSet</code> removes the event registration currently associated with the approaching expiration of the set's lease. It is acceptable to call this method even if there is no active registration.
+</p>
+<p class="Body">
+  <a name="1001640"> </a>The <code>setRenewalFailureListener</code> method of <code>LeaseRenewalSet</code> allows the client to register for the event associated with the failure to renew a client lease in the set. These events are generated when a client lease in the set reaches its actual expiration before its desired expiration or when the service attempts to renew a client lease and gets a definite exception. The <code>listener</code> argument specifies the listener to be notified if a client lease could not be renewed. 
+</p>
+<p class="Body">
+  <a name="1001621"> </a>The <code>handback</code> argument to <code>setRenewalFailureListener</code> specifies an object that will be part of the renewal failure event notification. This mechanism is detailed in the <a href="event-spec.html"><em class="Emphasis">Jini Distributed Events Specification</em></a>.
+</p>
+<p class="Body">
+  <a name="1012121"> </a>The <code>setRenewalFailureListener</code> method returns the event registration for this event. The <code>Lease</code> object associated with the registration will be equivalent (in the sense of the <code>equals</code> method) to the <code>Lease</code> on the renewal set. Because the event registration shares a lease with the set, clients that want to just remove their expiration warning registration without destroying the set should use the <code>clearRenewalFailureListener</code> method (described below) instead of cancelling the registration's lease. The registration ID returned with the registration will be <code>LeaseRenewalSet.RENEWAL_FAILURE_EVENT_ID</code>. The source of the registration will be the set. The method will throw <code>NullPointerException</code> if the <code>listener</code> argument is <code>null</code>. If an event handler has already been specified for this event, the current registration is replaced with the new one. Because
  both registrations are for the same kind of event, the events sent to the new registration must be in the same sequence as the events sent to the old registration.
+</p>
+<p class="Body">
+  <a name="1001624"> </a>The <code>clearRenewalFailureListener</code> method of <code>LeaseRenewalSet</code> removes the event registration currently associated with the failure to renew client leases. It is acceptable to call this method even if there is no active registration.
+</p>
+<pre  class="Preformatted">
+package net.jini.lease;
+
+public class ExpirationWarningEvent extends RemoteEvent {
+    public ExpirationWarningEvent(
+            LeaseRenewalSet  source,
+            long             seqNum,
+            MarshalledObject handback) {...}
+    public Lease getRenewalSetLease() {...}
+<code>}
+</code></pre>
+<p class="Body">
+  <a name="1012140"> </a><code>ExpirationWarningEvent</code> objects are passed to the event handlers specified in calls to the <code>LeaseRenewalSet</code> method, <code>setExpirationWarningListener</code>. The <code>ExpirationWarningEvent</code> is a subclass of <code>RemoteEvent</code> and adds no additional state. Because the source of a <code>ExpirationWarningEvent</code> is the set that is about to expire, the lease that needs to be renewed can be obtained by: calling <code>getSource</code>, casting the result to a <code>LeaseRenewalSet</code> and then invoking the set's <code>getRenewalSetLease</code> method. The convenience method <code>getRenewalSetLease</code> in <code>ExpirationWarningEvent</code> uses  this technique to retrieve the lease on the set.  The <code>Lease</code> object returned will be equivalent (in the sense of the <code>equals</code> method) to other <code>Lease</code> objects associated with the set but may not be the same object. One notable cons
 equence of having two different objects is that the <code>getExpiration</code> method of the <code>Lease</code> object returned by the event's <code>getRenewalSetLease</code> method may return a different time than the <code>getExpiration</code> methods of other <code>Lease</code> objects granted on the same set.
+</p>
+<p class="Body">
+  <a name="1010427"> </a>The expiration time associated with the <code>Lease</code> object returned by the <code>getRenewalSetLease</code> method will reflect the expiration the lease had when the event occurred. Renewal calls may have changed the expiration time of the underlying lease between the time when the event was generated and when it was delivered. 
+</p>
+<p class="Body">
+  <a name="1010431"> </a>Other aspects of the event's state are described in the <a href="event-spec.html"><em class="Emphasis">Jini Distributed Events Specification</em></a>. Sequence numbers for a given event ID are increasing. If there is no gap between two sequence numbers, no events have been missed; if there is a gap, events might (but might not) have been missed.
+</p>
+<pre  class="Preformatted">
+package net.jini.lease;
+
+public abstract class RenewalFailureEvent
+    extends RemoteEvent
+{
+    public RenewalFailureEvent(LeaseRenewalSet  source,
+                               long             seqNum,
+                               MarshalledObject handback) {...}
+    abstract public Lease getLease() 
+        throws IOException, ClassNotFoundException;
+    abstract public Throwable getThrowable()
+        throws IOException, ClassNotFoundException;
+}
+</pre>
+<p class="Body">
+  <a name="1011660"> </a><code>RenewalFailureEvent</code> objects are passed to the event handlers specified in calls to the <code>LeaseRenewalSet</code> method, <code>setRenewalFailureListener</code>. The <code>RenewalFailureEvent</code> is a subclass of <code>RemoteEvent</code>, adding two additional items of abstract state: the client lease that could not be renewed before expiration and the <code>Throwable</code> object that was thrown by the last recorded renewal attempt (if any). The client lease is returned by the <code>getLease</code> method, and the <code>Throwable</code> object is returned by the <code>getThrowable</code> method. If the <code>Throwable</code> object is <code>null</code>, it can be assumed that during the time between the last-recorded, successful renewal (or when the client lease was added to the set if there have been no renewals) and the actual expiration time of the client lease the renewal service was either unable to attempt a renewal of the c
 lient lease, or that it attempted a renewal but was unable to record the result.
+</p>
+<p class="Body">
+  <a name="1006443"> </a>Both the <code>getLease</code> and <code>getThrowable</code> methods may throw <code>IOException</code> or <code>ClassNotFoundException</code>. This declaration allows implementations to delay unmarshalling this state until it is actually needed. Once either method of a given <code>RenewalFailureEvent</code> object returns normally, future calls on that method must return the same object and may not throw an exception. 
+</p>
+<p class="Body">
+  <a name="1001917"> </a>If the renewal service was able to renew the client lease and record the result before the event occurred, the expiration time of the <code>Lease</code> object returned by the event's <code>getLease</code> method will reflect the result of the last-recorded successful renewal call. Note that this time may be distorted by clock skew between hosts if it is currently set to use the <code>Lease.ABSOLUTE</code> serial format. If the <code>Lease</code> object is using the <code>Lease.DURATION</code> serial format, and the event only unmarshals the lease when <code>getLease</code> is called, the expiration time may be distorted if a long time has passed between the time the event was generated by the renewal service and when the client called <code>getLease</code>. When a renewal failure event is generated for a given lease, that lease is removed from the set.
+</p>
+<p class="Body">
+  <a name="1011496"> </a>The event's other state is described in the <a href="event-spec.html"><em class="Emphasis">Jini Distributed Events Specification</em></a>.
+ Sequence numbers for a given event ID are increasing. If there is no gap between two sequence numbers, no events have been missed; if there is a gap, events might (but might not) have been missed.
+</p>
+<h4 class="Heading3">
+  <a name="1011531"> </a>LR.2.2	 Serialized Forms
+<p><CENTER>
+<table border="1" bordercolorlight="#FFFFFF" bordercolordark="#000000"
+       cellpadding="5" cellspacing="0" summary="serialized forms of the following classes">
+  <caption></caption>
+  <tr bgcolor="#CCCCCC">
+    <th>Class<br></th>
+    <th>serialVersionUID<br></th>
+    <th>Serialized Fields<br></th>
+  </tr>
+  <tr>
+    <td><code>RenewalFailureEvent</code><br></td>
+    <td>889145704195932943L<br></td>
+    <td><em>none</em><br></td>
+  </tr>
+  <tr>
+    <td><code>ExpirationWarningEvent</code><br></td>
+    <td>-2020487536756927350L<br></td>
+  <td><em>none</em><br></td>
+  </tr>
+  <tr>
+    <td><code>LeaseUnmarshalException</code><br></td>
+    <td>-6736107321698417489L<br></td>
+    <td><code>Lease[]unmarshalledLeases</code><br>
+	<code>MarshalledObject[]</code><br>
+        <code>stillMarshalledLeases</code><br>
+	<code>Throwable[] exceptions</code><br></td>
+  </tr>
+</table>
+</CENTER>
+<h3 class="Heading2">
+  <a name="43987"> </a>LR.3	 History</h3>
+<p>
+<table align="center" border="1" bordercolorlight="#FFFFFF" bordercolordark="#000000" cellpadding="5" cellspacing="0" summary="history of this specification">
+  <caption><p class="Body">
+  <a name="01887"> </a>
+</p>
+</caption>
+  <tr bgcolor="#CCCCCC">
+    <th>Version</th>
+    <th>Description</th>
+  </tr>
+ <tr>
+    <td valign="top">v1.0
+	</td>
+    <td>Initial release of this specification.
+</td>
+  </tr>
+</table>
+
+<h3 class="Heading2">
+  <a name="0188"> </a>		 License	 
+</h3>
+<p>
+Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership. The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License. You may obtain a copy of the License at
+<ul>
+     <a href="http://www.apache.org/licenses/LICENSE-2.0">http://www.apache.org/licenses/LICENSE-2.0</a>
+</ul>
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+</blockquote>
+
+<hr>
+<a href="#skip" title="Skip navigation bar"></a>
+<table width="100%"><tr>
+<td align=left><a href="../../spec-index.html">Spec Index</a>
+<td align=right><em>A Collection of Jini Technology Helper Utilities and Services Specifications</em></td>
+</tr></table>
+<a name="skip"></a>
+
+<hr>
+Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership. The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License. You may obtain a copy of the License at
+<ul>
+     <a href="http://www.apache.org/licenses/LICENSE-2.0">http://www.apache.org/licenses/LICENSE-2.0</a>
+</ul>
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+
+</body>
+</html>
+
+<!-- This HTML file was initially created with Quadralay WebWorks Publisher 3.5.0 -->
+<!-- by Susan Snyder -->
+<!-- Last updated: 01/27/05 -->
+

Added: incubator/river/site/trunk/content/river/doc/specs/html/mailbox-spec.html
URL: http://svn.apache.org/viewvc/incubator/river/site/trunk/content/river/doc/specs/html/mailbox-spec.html?rev=1052569&view=auto
==============================================================================
--- incubator/river/site/trunk/content/river/doc/specs/html/mailbox-spec.html (added)
+++ incubator/river/site/trunk/content/river/doc/specs/html/mailbox-spec.html Fri Dec 24 19:54:05 2010
@@ -0,0 +1,419 @@
+<!--
+ ! Licensed to the Apache Software Foundation (ASF) under one
+ ! or more contributor license agreements.  See the NOTICE file
+ ! distributed with this work for additional information
+ ! regarding copyright ownership. The ASF licenses this file
+ ! to you under the Apache License, Version 2.0 (the
+ ! "License"); you may not use this file except in compliance
+ ! with the License. You may obtain a copy of the License at
+ ! 
+ !      http://www.apache.org/licenses/LICENSE-2.0
+ ! 
+ ! Unless required by applicable law or agreed to in writing, software
+ ! distributed under the License is distributed on an "AS IS" BASIS,
+ ! WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ! See the License for the specific language governing permissions and
+ ! limitations under the License.
+ !-->
+
+<html>
+
+<head>
+<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
+<meta name="GENERATOR" content="Quadralay WebWorks Publisher 5.0.4">
+<link rel="StyleSheet" href="standard.css" type="text/css" media="screen">
+<title>Jini Event Mailbox Service Specification  </title>
+</head>
+
+<body bgcolor="#ffffff">
+
+<p> </p>
+<a href="#skip" title="Skip navigation bar"></a>
+<table width="100%">
+<tr>
+<td align=left><a href="../../spec-index.html">Spec Index</a></td>
+<td align=right><i>A Collection of Jini Technology Helper Utilities and Services Specifications
+</i></td>
+</tr>
+</table>
+<a name="skip"></a>
+<br clear="all">
+
+
+<hr align="left">
+<table width="90%">
+<tr>
+<td align="right" font size="4"><b>Version 2.0</b></td>
+</tr>
+</table>
+<blockquote>
+<h2>
+  <a name="1005479"> </a>EM - Jini<font size="-1"><sup>TM</sup></font> Event Mailbox Service Specification
+</h2>
+<h3 class="Heading2">
+  <a name="1000110"> </a>EM.1	 Introduction
+</h3>
+<p class="Body">
+  <a name="1001466"> </a>The <a href="event-spec.html"><em class="Emphasis">Jini<font size="-1"><sup>TM</sup></font> Distributed Events Specification</em></a> states the ability to interpose third-party objects, or "agents," into an event notification chain as one of its design goals. This specification also describes a notification mailbox object, which stores and forwards event notifications on behalf of other objects, as an example of a useful third-party agent. These mailbox objects can be particularly helpful for objects that need more control over how and when they receive event notifications.
+</p>
+<p class="Body">
+  <a name="1009565"> </a>For example, it would be impossible to send event notifications to a transient entity that has detached itself from a system of Jini<font size="-1"><sup>TM</sup></font> technology-enabled services and/or devices (<em class="Emphasis">Jini system</em>). In such a situation an entity could employ the services of an event mailbox to store event notifications on its behalf before leaving the system. Upon rejoining the Jini system, the entity could then contact the event mailbox to retrieve any collected events that it would otherwise have missed. Similarly, an entity that wishes to deactivate could use an event mailbox to collect event notifications on its behalf while dormant.
+</p>
+<p class="Body">
+  <a name="1005881"> </a>Like other Jini technology-enabled services (<em class="Emphasis">Jini services</em>), the event mailbox service will grant its services only for a limited period of time without an active expression of continuing interest. Therefore, event mailbox clients still need to renew their leases if they intend to maintain the mailbox's services beyond the initially granted lease period. Any resources (for example, remote objects or storage space) associated with a particular client can be freed once the client's lease has expired or been cancelled. In the previous usage scenarios, it might also benefit a transient or deactivatable entity to employ the services of a lease renewal service (see the <a href="lrs-spec.html"><em class="Emphasis">Jini Lease Renewal Service Specification</em></a>) to help mitigate the issue of lease maintenance.
+</p>
+<p class="Body">
+  <a name="1009032"> </a>The remainder of this specification defines the requirements, interfaces, and protocols of the event mailbox service.
+</p>
+<h4 class="Heading3">
+  <a name="1000115"> </a>EM.1.1	 Goals and Requirements
+</h4>
+<p class="Body">
+  <a name="1000303"> </a>The requirements of the set of interfaces specified in this document are:
+</p>
+<ul>
+
+  <li class="SmartList1"><a name="1000304"> </a>To define a service that is capable of storing event notifications on behalf of its clients and capable of delivering stored event notifications to those clients upon request<p>
+  <li class="SmartList1"><a name="1005900"> </a>To provide this service in such a way that it can be used by entities that are temporarily unable or unwilling to receive event notifications<p>
+  <li class="SmartList1"><a name="1000305"> </a>To provide a service that complies with the policies embodied in the Jini technology programming model
+</ul>
+
+<p class="Body">
+  <a name="1005921"> </a>The goals of this specification are:
+</p>
+<ul>
+
+  <li class="SmartList1"><a name="1005926"> </a>To describe the event mailbox service<p>
+  <li class="SmartList1"><a name="1005931"> </a>To provide guidance in the use and deployment of the event mailbox service
+</ul>
+
+<h4 class="Heading3">
+  <a name="1000302"> </a>EM.1.2	 Other Types
+</h4>
+<p class="Body">
+  <a name="1000008"> </a>The types defined in the specification of the event mailbox service are in the <code>net.jini.event</code> package. This specification assumes knowledge of the <a href="event-spec.html"><em class="Emphasis">Jini Distributed Events Specification</em></a> and the <a href="lease-spec.html"><em class="Emphasis">Jini Distributed Leasing Specification</em></a>. The following object types may be referenced in this chapter. Whenever referenced, these object types will be referenced in unqualified form:
+</p>
+<p class="Body">
+  <a name="1009048"> </a>
+</p>
+<pre  class="Preformatted">
+java.rmi.NoSuchObjectException
+java.rmi.RemoteException
+net.jini.core.event.RemoteEvent
+net.jini.core.event.RemoteEventListener
+net.jini.core.lease.Lease
+net.jini.core.lease.LeaseDeniedException
+</pre>
+<h3 class="Heading2">
+  <a name="1001523"> </a>EM.2	 The Interface
+</h3>
+<p class="Body">
+  <a name="1009792"> </a>The <code>EventMailbox</code> defines the interface to the event mailbox service. Through this interface, other Jini services and clients may request that event notification management be performed on their behalf. This interface belongs to the <code>net.jini.event</code> package, and any service implementing this interface must comply with the definition of a Jini service. This interface is not a remote interface; each implementation exports a proxy object that implements this interface local to the client, using an implementation-specific protocol to communicate with the actual remote server. All of the proxy methods obey normal Java<font size="-1"><sup>TM</sup></font> Remote Method Invocation (Java RMI) interface semantics and can therefore be implemented directly using Java RMI (except where explicitly noted). Two proxy objects are equal (using the <code>equals</code> method) if they are proxies for the same event mailbox service.
+</p>
+<pre  class="Preformatted">
+package net.jini.event;
+
+public interface EventMailbox
+{
+    MailboxRegistration register(long leaseDuration)
+        throws RemoteException, LeaseDeniedException;
+}
+</pre>
+<p class="Body">
+  <a name="1002029"> </a>
+</p>
+<p class="Body">
+  <a name="1009773"> </a>Event mailbox clients wishing to use the mailbox service first register themselves with the service using the <code>register</code> method. Clients then use the methods of the returned <code>MailboxRegistration</code> object (a <em class="Emphasis">registration</em>) in order to:
+</p>
+<ul>
+
+  <li class="SmartList1"><a name="1006019"> </a>Manage the lease for this particular registration<p>
+  <li class="SmartList1"><a name="1006024"> </a>Obtain a <code>RemoteEventListener</code> reference that can be registered with <em class="Emphasis">event generators</em> (that is, objects that support event notification for changes in their abstract state). This listener will store any received notifications for this particular registration.<p>
+  <li class="SmartList1"><a name="1006029"> </a>Enable or disable the delivery of any stored notifications for this particular registration
+</ul>
+
+<h3 class="Heading2">
+  <a name="1002030"> </a>EM.3	 The Semantics
+</h3>
+<p class="Body">
+  <a name="1009820"> </a>To employ the event mailbox service, a client must first register with the event mailbox service by invoking the <code>EventMailbox</code> interface's only method, <code>register</code>. Each invocation of the <code>register</code> method produces a new registration.
+</p>
+<p class="Body">
+  <a name="1009847"> </a>The <code>register</code> method may throw a <code>RemoteException</code> or a <code>LeaseDeniedException</code>. Typically, a <code>RemoteException</code> occurs when there is a communication failure between the client and the event mailbox service. If this exception does occur, the registration may or may not have been successful. A <code>LeaseDeniedException</code> is thrown if the event mailbox service is unable or unwilling to grant the registration request. It is implementation specific as to whether or not subsequent attempts (with or without the same argument) are likely to succeed.
+</p>
+<p class="Body">
+  <a name="1001539"> </a>Each registration with the event mailbox service is persistent across restarts or crashes of the event mailbox service, until the lease on the registration expires or is cancelled.
+</p>
+<p class="Body">
+  <a name="1001803"> </a>The <code>register</code> method takes a single parameter of type <code>long</code> that represents the requested initial lease duration for the registration, in milliseconds. This duration value must be positive (except for the special value of <code>Lease.ANY</code>). Otherwise, an <code>IllegalArgumentException</code> is thrown.
+</p>
+<p class="Body">
+  <a name="1008949"> </a>Every method invocation on an event mailbox service (whether the invocation is directly on the service, or indirectly on a <code>MailboxRegistration</code> that the service has created) is atomic with respect to other invocations.
+</p>
+<p class="Body">
+  <a name="1008947"> </a>
+</p>
+<h3 class="Heading2">
+  <a name="1009616"> </a>EM.4	 Supporting Interfaces and Classes
+</h3>
+<p class="Body">
+  <a name="1009617"> </a>The <code>register</code> method returns an object that implements the interface <code>MailboxRegistration</code>. It is through this interface that the client controls its registration and notification management with the event mailbox service.
+</p>
+<pre  class="Preformatted">
+package net.jini.event;
+
+public interface MailboxRegistration
+{
+    Lease getLease();
+    RemoteEventListener getListener();
+    void enableDelivery(RemoteEventListener target)
+        throws RemoteException;
+    void disableDelivery() throws RemoteException;
+}
+</pre>
+<p class="Body">
+  <a name="1002176"> </a>The <code>MailboxRegistration</code> interface is not a remote interface. Each implementation of the event mailbox service exports proxy objects that implement this interface local to the client. These proxies use an implementation-specific protocol to communicate with the remote server. All of the remote proxy methods obey normal Java RMI interface semantics and can therefore be implemented using Java RMI. Two proxy objects are equal (using the <code>equals</code> method) if they are proxies for the same registration, created by the same event mailbox service.
+</p>
+<p class="Body">
+  <a name="1002187"> </a>Each remote method of this interface may throw a <code>RemoteException</code>. Typically, this exception occurs when there is a communication failure between the client and the event mailbox service. Whenever a method invocation results in a <code>RemoteException</code>, the method may or may not have successfully completed.
+</p>
+<p class="Body">
+  <a name="1006083"> </a>Any invocation of a remote method defined in this interface will result in a <code>NoSuchObjectException</code> if the client's registration with the event mailbox service has expired or has been cancelled. Note that upon receipt of a <code>NoSuchObjectException</code>, the client can assume that the registration no longer exists; the client cannot assume that the event mailbox service itself no longer exists.
+</p>
+<h4 class="Heading3">
+  <a name="1006088"> </a>EM.4.1	 The Semantics
+</h4>
+<p class="Body">
+  <a name="1009632"> </a>The <code>getLease</code> method returns the <code>Lease</code> object associated with the registration. The client can renew or cancel the registration with the mailbox service through the <code>Lease</code> object returned by this method (see the <a href="lease-spec.html"><em class="Emphasis">Jini Distributed Leasing Specification</em></a>). This method is not remote and takes no arguments.
+</p>
+<p class="Body">
+  <a name="1006102"> </a>The <code>getListener</code> method returns an object that implements the interface <code>RemoteEventListener</code>. This object, referred to as a <em class="Emphasis">mailbox listener</em>, can then be submitted as the <code>RemoteEventListener</code> argument to an event generator's registration method(s) (see the <a href="event-spec.html"><em class="Emphasis">Jini Distributed Events Specification</em></a>). Subsequent calls to this method will return equivalent objects (in the <code>equals</code> sense). Note that mailbox listeners generated by different registrations will not be equal. This method is not remote and takes no arguments.
+</p>
+<p class="Body">
+  <a name="1006111"> </a>The valid period of use for a mailbox listener is tied to the associated registration's lease. A <code>NoSuchObjectException</code> will be thrown if an attempt is made to invoke the <code>notify</code> method on a mailbox listener whose associated lease has terminated.
+</p>
+<p class="Body">
+  <a name="1006116"> </a>Mailbox listener references, just like their associated registrations, are persistent across server restarts or crashes until their associated registration's lease terminates.
+</p>
+<p class="Body">
+  <a name="1006123"> </a>The <code>enableDelivery</code> method allows a client to initiate delivery of event notifications (received on its behalf by this particular registration) to the client-specified listener, referred to as the <em class="Emphasis">target listener</em>. This method takes a single argument of type <code>RemoteEventListener</code>. Subsequent calls to this method simply replace the registration's existing target listener, if any, with the specified target listener. Passing <code>null</code> as the listener argument has the same effect as disabling delivery (see below).
+</p>
+<p class="Body">
+  <a name="1006135"> </a>Resubmitting a mailbox listener back to the same mailbox service that generated it will result in an <code>IllegalArgumentException</code> being thrown. This is necessary to prevent a recursive event notification chain. Therefore, the event mailbox service must keep track of any listener objects that it generates and reject the resubmission of those objects.
+</p>
+<p class="Body">
+  <a name="1006124"> </a>Once enabled, event delivery remains enabled until it is disabled. Any events received while delivery is enabled will also be scheduled for delivery.
+</p>
+<p class="Body">
+  <a name="1006145"> </a>Event delivery guarantees with respect to exception handling, ordering, and concurrency are implementation specific and are not specified in this document. However, implementations are encouraged to support the following functionality. If an event delivery attempt produces an exception that indicates future attempts might be successful (an indefinite exception), then reasonable efforts should be made to successfully redeliver the event until the associated registration's lease terminates. On the other hand, if an event delivery attempt produces an exception that indicates future attempts will be unsuccessful (a definite exception), then event delivery should be disabled for the associated registration until it is explicitly enabled again. 
+</p>
+<p>
+The algorithm used to classify exceptions as definite or indefinite is implementation specific.
+</p>
+<p class="Body">
+  <a name="1009346"> </a>Also, implementations may concurrently deliver event notifications to the same target listener, which implies that events may be sent in a different order than the order in which they were originally received. Hence, it is the target listener's responsibility to guard against potential concurrent, out-of-order event delivery. 
+</p>
+<p class="Body">
+  <a name="1006146"> </a>Similarly, implementations are encouraged to support this method's intended semantics regarding listener replacement. That is, a mailbox client can reasonably assume that listener replacement has occurred upon successful return from this method and can therefore safely unexport the previous listener object. This also implies that any in-progress delivery attempts to the previous listener are either successfully cancelled before returning from this method (blocking), or subsequently retried using the replacement listener after returning from this method (non-blocking). Note that the non-blocking case can potentially allow the previous listener to be notified after successfully returning from this method.
+</p>
+<p class="Body">
+  <a name="1006158"> </a>The <code>disableDelivery</code> method allows the client to cease event delivery to the existing target listener, if any. It is acceptable to call this method even if no target listener is currently enabled. This method takes no arguments. 
+</p>
+<p class="Body">
+  <a name="1006159"> </a>Again, event delivery guarantees are implementation specific and are not specified in this document. Implementations are encouraged to support the method's intended semantics regarding delivery suspension. That is, a mailbox client can reasonably assume that event delivery has been suspended upon successful return from this method and can therefore safely unexport the previously enabled listener object if desired. This also implies that any in-progress delivery attempts to the previously enabled listener are either successfully cancelled before returning from this method (blocking), or subsequently retried using the next enabled listener after returning from this method (non-blocking). Note that the non-blocking case can potentially allow the previously enabled listener to be notified after successfully returning from this method.
+</p>
+<p class="Body">
+  <a name="1006161"> </a>The event mailbox service does not normally concern itself with the attributes of the <code>RemoteEvent</code>s that it receives. The one circumstance about which it must concern itself is when a target listener throws an <code>UnknownEventException</code> during an event delivery attempt. The event mailbox service must maintain a list, on a per-registration basis, of the particular combinations of event identifier and source reference (obtained from the offending <code>RemoteEvent</code> object) that produced the exception. The event mailbox must then propagate an <code>UnknownEventException</code> back to any event generator that attempts to deliver a <code>RemoteEvent</code> with an identifier-source combination held in a registration's unknown exception list. The service will also skip the future delivery of any stored events that have an identifier-source combination held in this list.
+</p>
+<p class="Body">
+  <a name="1009476"> </a>A registration's unknown exception list is cleared upon re-enabling delivery with any target listener. This list is persistent across service restarts or crashes, until the associated registration's lease terminates.
+</p>
+<p class="Body">
+  <a name="1009474"> </a>Note that the act of comparing event source objects for equality may pose a security risk because source objects are potentially given references to other source objects that are currently using the same mailbox. If security is a concern, then care should be taken to prevent independent event sources from obtaining information about each other, for example by using a separate mailbox for each source. 
+</p>
+<p class="Body">
+  <a name="1006191"> </a>The event mailbox does not support multiple, concurrent notification targets per registration. As a result, the interface supports only a set/clear model rather than the more common add/remove model.
+</p>
+<p class="Body">
+  <a name="1009395"> </a>Event persistence guarantees are not specified in this document because no single policy can cover all the possible design trade-offs between reliability, efficiency, and performance. It is expected that operational parameters--controls for how the event mailbox deals with issues such as persistence guarantees, storage quotas, and low space behavior--will be exposed through an administration interface, which can vary across different event mailbox implementations.
+</p>
+<h3 class="Heading2">
+  <a name="1009616"> </a>EM.5	 The Interface
+</h3>
+<p class="Body">
+The <code>PullEventMailbox</code> defines the interface to the pull event mailbox service (the mailbox service). Through this interface, other Jini technology-enabled services and clients may request that event notification management be performed on their behalf. This interface belongs to the <code>net.jini.event</code> package. This interface is not a remote interface; each implementation exports a proxy object that implements this interface local to the client, using an implementation-specific protocol to communicate with the actual remote server. All of the proxy methods obey normal Java RMI interface semantics and can therefore be implemented directly using Java RMI. Two proxy objects are equal (using the <code>equals</code> method) if they are proxies for the same mailbox service.
+<pre>
+package net.jini.event;
+
+public interface PullEventMailbox extends EventMailbox 
+{
+    MailboxPullRegistration pullRegister(long leaseDuration)
+        throws RemoteException, LeaseDeniedException;
+}
+
+
+</pre>
+<p class="Body">
+Clients wishing to use the mailbox service first register themselves with the service using the <code>pullRegister</code> method. Clients then use the methods of the returned <code>MailboxPullRegistration</code> object (a registration) to:
+<UL>
+<LI>Manage the lease for this particular registration.
+<LI>Obtain a <code>RemoteEventListener</code> reference that can be registered with event generators (that is, objects that support event notification for changes in their abstract state). This listener will store event notifications on behalf of this particular registration.
+<LI>Synchronously or asynchronously collect any event notifications stored by this particular registration.
+</UL>
+<h3 class="Heading2">
+  <a name="2031"> </a>EM.6	 The Semantics
+</h3>
+<p class="Body">
+To employ the mailbox service, a client must first register with the mailbox service by invoking the <code>pullRegister</code> method. Each invocation of the <code>pullRegister</code> method produces a new registration object. Each registration is persistent across restarts or crashes of the mailbox service until the registration's lease expires or is canceled.
+<p class="Body">
+The <code>pullRegister</code> method takes a single parameter of type <code>long</code> that represents the requested initial lease duration for the registration, in milliseconds. This duration value must be positive (except for the special value of <code>Lease.ANY</code>). Otherwise, an <code>IllegalArgumentException</code> is thrown.
+<p class="Body">
+The <code>pullRegister</code> method may throw a <code>RemoteException</code> or a <code>LeaseDeniedException</code>. Typically, a <code>RemoteException</code> occurs when there is a communication failure between the client and the event mailbox service. If this exception does occur, the registration may or may not have been successful. A <code>LeaseDeniedException</code> is thrown if the mailbox service is unable or unwilling to grant the registration request. If <code>LeaseDeniedException</code> is thrown, it is implementation specific as to whether or not subsequent attempts (with the same or a different argument value) are likely to succeed.
+<p class="Body">
+Every method invocation on a mailbox service (whether the invocation is directly on the service, or indirectly on a registration that the service has created) is atomic with respect to other invocations.
+
+<h3 class="Heading2">
+  <a name="2032"> </a>EM.7	 Supporting Interfaces and Classes
+</h3>
+<p class="Body">
+The <code>pullRegister</code> method returns an object that implements the <code>MailboxPullRegistration</code> interface. It is through this interface that the client controls its registration and notification management with the mailbox service.
+
+</p>
+<pre  class="Preformatted">
+package net.jini.event;
+
+public interface MailboxPullRegistration extends 
+    MailboxRegistration 
+{
+    RemoteEventIterator getRemoteEvents() 
+        throws RemoteException;
+    void addUnknownEvents(Collection unknownEvents)
+        throws RemoteException;
+}
+public interface RemoteEventIterator 
+{
+    RemoteEvent next(long timeout)
+        throws RemoteException, InvalidIteratorException;
+    void close() throws InvalidIteratorException;
+}
+public class InvalidIteratorException extends Exception
+{
+    public InvalidIteratorException(String reason);
+    public InvalidIteratorException();
+}
+</pre>
+<p class="Body">
+The <code>MailboxPullRegistration</code> and the <code>RemoteEventIterator</code> interfaces are not remote interfaces. Each implementation of the mailbox service exports proxy objects that implement these interfaces locally to the client. These proxies use an implementation-specific protocol to communicate with the remote server. All of the remote proxy methods obey normal Java RMI interface semantics and can therefore be implemented using Java RMI. Two proxy objects are equal (using the <code>equals</code> method) if they are proxies for the same registration, created by the same mailbox service.
+<p class="Body">
+Each remote method of these interfaces may throw a <code>RemoteException</code>. Typically, this exception occurs when there is a communication failure between the client and the mailbox service. Whenever a method invocation results in a <code>RemoteException</code>, the method may or may not have successfully completed.
+<p class="Body">
+Any invocation of a remote method defined in this interface will result in a <code>NoSuchObjectException</code> if the client's registration with the mailbox service has expired or has been canceled. Note that upon receipt of a <code>NoSuchObjectException</code>, the client can assume that the registration no longer exists; the client cannot assume that the mailbox service itself no longer exists.
+<h4 class="Heading3">
+  <a name="20321"> </a>EM.7.1	 The Semantics
+</h4>
+
+<p class="Body">
+The <code>getRemoteEvents</code> method returns a <code>RemoteEventIterator</code> object (an iterator) associated with the registration. The client can retrieve event notifications (received on its behalf by this particular registration) from the mailbox service through the iterator returned by this method.
+
+<p class="Body">
+Each invocation of the <code>getRemoteEvents</code> method produces a new iterator. Each new iterator will invalidate all previous iterators produced by the same registration. An invalidated iterator's methods must eventually throw an <code>InvalidIteratorException</code> to indicate this condition.
+
+<p class="Body">
+Calling <code>getRemoteEvents</code> also effectively calls <code>disableDelivery</code> for the associated registration. This will disable the registration's associated target listener, if any. Conversely, calling <code>enableDelivery</code> will, in turn, invalidate any existing iterators produced by the same registration.
+
+<p class="Body">
+If the combination of the event identifier and the event generator's object reference obtained from an event object is not one in which the mailbox client has registered an interest, an <code>UnknownEventException</code> should be propagated back to the event generator. This is accomplished by calling <code>addUnknownEvents</code> with a collection of unknown events. The effects of modifying the collection of unknown events during a call to <code>addUnknownEvents</code> are undefined.
+
+<p class="Body">
+The mailbox service will maintain a list of unknown events, on a per-registration basis, with the particular combinations of event identifier and source reference (obtained from the provided event objects). The mailbox should then propagate an <code>UnknownEventException</code> back to any event generator that attempts to deliver an event with an identifier-source combination held in a registration's unknown exception list. The valid iterator associated with the registration should also eventually skip the future delivery of any stored events that have an identifier-source combination held in this list.
+
+<p class="Body">
+A registration's unknown exception list is persistent across service restarts or crashes, until the associated registration's lease terminates or is cleared by subsequent calls to either <code>enableDelivery</code> or <code>getRemoteEvents</code>.
+
+<p class="Body">
+<code>RemoteEventIterator</code>'s next method returns either an event from the registration's set of events (event set) or <code>null</code> if the event set is empty. This method takes a single argument of type <code>long</code>, which is the maximum time, in milliseconds, to wait for an event to become available in the event set. This argument must be a non-negative number or an <code>IllegalArgumentException</code> will be thrown. An iterator will not redeliver an event once it has been successfully returned from that iterator.
+
+<p class="Body">
+In general, events may be transferred to the client during or after the <code>getRemoteEvents</code> call. If there are <code>InvocationConstraints</code> associated with the <code>getRemoteEvents</code> call, then all of the events returned by <code>next</code> will be transferred in a way that meets those constraints. In particular, any constraints associated with the <code>next</code> method are ignored. The <code>next</code> method may return events after the associated registration lease has expired.
+
+<p class="Body">
+The <code>next</code> method may throw an <code>InvalidIteratorException</code>. An <code>InvalidIteratorException</code> is thrown if <code>enableDelivery</code> was subsequently called for this registration, a new iterator was subsequently generated for this registration, or the iterator was closed. Subsequent invocations (with the same or different argument value) will also fail with the same exception once an iterator throws <code>InvalidIteratorException</code>.
+
+<p class="Body">
+Calling <code>close</code> ends all event processing being performed by the iterator and invalidates the iterator. Subsequent iterator method invocations will also throw <code>InvalidIteratorException</code>. Any additional termination semantics must be defined by the implementation class itself.
+
+<h3 class="Heading2">
+  <a name="2034"> </a>EM.8	 History
+</h3>
+<p>
+<table align="center" border="1" bordercolorlight="#FFFFFF" bordercolordark="#000000" cellpadding="5" cellspacing="0" summary="history of this specification">
+  <caption><p class="Body">
+  <a name="01887"> </a>
+</p>
+</caption>
+  <tr bgcolor="#CCCCCC">
+    <th>Version</th>
+    <th>Description</th>
+  </tr>
+<tr>
+  <td>v1.0</td>
+  <td>Initial release of this specification.</td>
+</tr>
+<tr>
+  <td>v2.0</td>
+  <td>Added "pull" semantics to mailbox specification (sections EM.5 through EM.8)<br>
+      Changed titles for former "Core" specifications</td>
+</tr>
+</table>
+<h3 class="Heading2">
+  <a name="0188"> </a>		 License	 
+</h3>
+<p>
+Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership. The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License. You may obtain a copy of the License at
+<ul>
+     <a href="http://www.apache.org/licenses/LICENSE-2.0">http://www.apache.org/licenses/LICENSE-2.0</a>
+</ul>
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+</blockquote>
+
+<hr>
+<a href="#skip" title="Skip navigation bar"></a>
+<table width="100%"><tr>
+<td align=left><a href="../../spec-index.html">Spec Index</a>
+<td align=right><i>A Collection of Jini Technology Helper Utilities and Services Specifications</i></td>
+</tr></table>
+<a name="skip"></a>
+
+<hr>
+Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership. The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License. You may obtain a copy of the License at
+<ul>
+     <a href="http://www.apache.org/licenses/LICENSE-2.0">http://www.apache.org/licenses/LICENSE-2.0</a>
+</ul>
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+
+</body>
+</html>
+
+<!-- This HTML file was created with Quadralay WebWorks Publisher 3.5.0 -->
+<!-- by Susan Snyder -->
+<!-- Last updated: 01/27/05 -->