1 /* 2 * Licensed to the Apache Software Foundation (ASF) under one 3 * or more contributor license agreements. See the NOTICE file 4 * distributed with this work for additional information 5 * regarding copyright ownership. The ASF licenses this file 6 * to you under the Apache License, Version 2.0 (the 7 * "License"); you may not use this file except in compliance 8 * with the License. You may obtain a copy of the License at 9 * 10 * http://www.apache.org/licenses/LICENSE-2.0 11 * 12 * Unless required by applicable law or agreed to in writing, software 13 * distributed under the License is distributed on an "AS IS" BASIS, 14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15 * See the License for the specific language governing permissions and 16 * limitations under the License. 17 */ 18 19 package net.jini.jeri; 20 21 import java.io.InputStream; 22 import java.io.OutputStream; 23 import java.util.Collection; 24 import net.jini.core.constraint.ConstraintAlternatives; 25 import net.jini.core.constraint.Integrity; 26 import net.jini.core.constraint.InvocationConstraints; 27 28 /** 29 * Represents a request that is being sent and the corresponding 30 * response received in reply. 31 * 32 * <p>An <code>OutboundRequest</code> can be used to write out the 33 * contents of the request and to read in the response. 34 * 35 * <p>The communication protocol used by the implementation of this 36 * interface must guarantee that for each instance of this interface, 37 * any request data must only be delivered to the recipient (in the 38 * form of an <code>InboundRequest</code> passed to {@link 39 * RequestDispatcher#dispatch RequestDispatcher.dispatch}) <i>at most 40 * once</i>. The {@link #getDeliveryStatus getDeliveryStatus} method 41 * can be used to determine whether or not at least partial delivery 42 * of the request might have occurred. 43 * 44 * <p>When finished using an <code>OutboundRequest</code>, in order to 45 * allow the implementation to free resources associated with the 46 * request, users should either invoke <code>close</code> on the 47 * streams returned by the <code>getRequestOutputStream</code> and 48 * <code>getResponseInputStream</code> methods, or invoke the 49 * <code>abort</code> method. 50 * 51 * @author Sun Microsystems, Inc. 52 * @see InboundRequest 53 * @since 2.0 54 **/ 55 public interface OutboundRequest { 56 57 /** 58 * Populates the supplied collection with context information 59 * representing this request. 60 * 61 * @param context the context collection to populate 62 * 63 * @throws NullPointerException if <code>context</code> is 64 * <code>null</code> 65 * 66 * @throws UnsupportedOperationException if <code>context</code> 67 * is unmodifiable and if any elements need to be added 68 **/ 69 void populateContext(Collection context); 70 71 /** 72 * Returns the requirements that must be at least partially 73 * implemented by higher layers in order to fully satisfy the 74 * requirements for this request. This method may also return 75 * preferences that must be at least partially implemented by 76 * higher layers in order to fully satisfy some of the preferences 77 * for this request. 78 * 79 * <p>For any given constraint, there must be a clear delineation 80 * of which aspects (if any) must be implemented by the transport 81 * layer. This method must not return a constraint (as a 82 * requirement or a preference, directly or as an element of 83 * another constraint) unless this request implements all of those 84 * aspects. Also, this method must not return a constraint for 85 * which all aspects must be implemented by the transport layer. 86 * Most of the constraints in the {@link net.jini.core.constraint} 87 * package must be fully implemented by the transport layer and 88 * thus must not be returned by this method; the one exception is 89 * {@link Integrity}, for which the transport layer is responsible 90 * for the data integrity aspect and higher layers are responsible 91 * for the code integrity aspect. 92 * 93 * <p>For any {@link ConstraintAlternatives} in the constraints 94 * for this request, this method should only return a 95 * corresponding constraint if all of the alternatives satisfied 96 * by this request need to be at least partially implemented by 97 * higher layers in order to be fully satisfied. 98 * 99 * @return the constraints for this request that must be partially 100 * or fully implemented by higher layers 101 **/ 102 InvocationConstraints getUnfulfilledConstraints(); 103 104 /** 105 * Returns an <code>OutputStream</code> to write the request data 106 * to. The sequence of bytes written to the returned stream will 107 * be the sequence of bytes sent as the body of this request. 108 * 109 * <p>After the entirety of the request has been written to the 110 * stream, the stream's <code>close</code> method must be invoked 111 * to ensure complete delivery of the request. It is possible 112 * that none of the data written to the returned stream will be 113 * delivered before <code>close</code> has been invoked (even if 114 * the stream's <code>flush</code> method had been invoked at any 115 * time). Note, however, that some or all of the data written to 116 * the stream may be delivered to (and processed by) the recipient 117 * before the stream's <code>close</code> method has been invoked. 118 * 119 * <p>After the stream's <code>close</code> method has been 120 * invoked, no more data may be written to the stream; writes 121 * subsequent to a <code>close</code> invocation will fail with an 122 * <code>IOException</code>. 123 * 124 * <p>If this method is invoked more than once, it will always 125 * return the identical stream object that it returned the first 126 * time (although the stream may be in a different state than it 127 * was upon return from the first invocation). 128 * 129 * @return the output stream to write request data to 130 **/ 131 OutputStream getRequestOutputStream(); 132 133 /** 134 * Returns an <code>InputStream</code> to read the response data 135 * from. The sequence of bytes produced by reading from the 136 * returned stream will be the sequence of bytes received as the 137 * response data. When the entirety of the response has been 138 * successfully read, reading from the stream will indicate an 139 * EOF. 140 * 141 * <p>Users of an <code>OutboundRequest</code> must not expect any 142 * data to be available from the returned stream before the 143 * <code>close</code> method has been invoked on the stream 144 * returned by <code>getRequestOutputStream</code>; in other 145 * words, the user's request/response protocol must not require 146 * any part of a request to be a function of any part of its 147 * response. 148 * 149 * <p>It is possible, however, for data to be available from the 150 * returned stream before the <code>close</code> method has been 151 * invoked on, or even before the entirety of the request has been 152 * written to, the stream returned by 153 * <code>getRequestOutputStream</code>. Because such an early 154 * response might indicate, depending on the user's 155 * request/response protocol, that the recipient will not consider 156 * the entirety of the request, perhaps due to an error or other 157 * abnormal condition, the user may wish to process it 158 * expeditiously, rather than continuing to write the remainder of 159 * the request. 160 * 161 * <p>Invoking the <code>close</code> method of the returned 162 * stream will cause any subsequent read operations on the stream 163 * to fail with an <code>IOException</code>, although it will not 164 * terminate this request as a whole; in particular, the request 165 * may still be subsequently written to the stream returned by the 166 * <code>getRequestOutputStream</code> method. After 167 * <code>close</code> has been invoked on both the returned stream 168 * and the stream returned by <code>getRequestOutputStream</code>, 169 * the implementation may free all resources associated with this 170 * request. 171 * 172 * <p>If this method is invoked more than once, it will always 173 * return the identical stream object that it returned the first 174 * time (although the stream may be in a different state than it 175 * was upon return from the first invocation). 176 * 177 * @return the input stream to read response data from 178 **/ 179 InputStream getResponseInputStream(); 180 181 /** 182 * Returns <code>false</code> if it is guaranteed that no data 183 * written for this request has been processed by the recipient. 184 * This guarantee remains valid until any subsequent I/O operation 185 * has been attempted on this request. 186 * 187 * If this method returns <code>true</code>, then data written for 188 * this request may have been at least partially processed by the 189 * recipient (the <code>RequestDispatcher</code> receiving the 190 * corresponding <code>InboundRequest</code>). 191 * 192 * @return <code>false</code> if data written for this request has 193 * definitely not been processed by the recipient, and 194 * <code>true</code> if data written for this request may have 195 * been at least partially processed by the recipient 196 **/ 197 boolean getDeliveryStatus(); 198 199 /** 200 * Terminates this request, freeing all associated resources. 201 * 202 * <p>This method may be invoked at any stage of the processing of 203 * the request. 204 * 205 * <p>After this method has been invoked, I/O operations on the 206 * streams returned by the <code>getRequestOutputStream</code> and 207 * <code>getResponseInputStream</code> methods will fail with an 208 * <code>IOException</code>, except some operations that may 209 * succeed because they only affect data in local I/O buffers. 210 * 211 * <p>If this method is invoked before the <code>close</code> 212 * method has been invoked on the stream returned by 213 * <code>getRequestOutputStream</code>, there is no guarantee that 214 * any or none of the data written to the stream so far will be 215 * delivered; the implication of such an invocation of this method 216 * is that the user is no longer interested in the successful 217 * delivery of the request. 218 **/ 219 void abort(); 220 }