• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2014 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package android.net;
18 
19 import android.os.Parcel;
20 import android.os.Parcelable;
21 
22 import java.util.Objects;
23 
24 /**
25  * Defines a request for a network, made through {@link NetworkRequest.Builder} and used
26  * to request a network via {@link ConnectivityManager#requestNetwork} or listen for changes
27  * via {@link ConnectivityManager#registerNetworkCallback}.
28  */
29 public class NetworkRequest implements Parcelable {
30     /**
31      * The {@link NetworkCapabilities} that define this request.
32      * @hide
33      */
34     public final NetworkCapabilities networkCapabilities;
35 
36     /**
37      * Identifies the request.  NetworkRequests should only be constructed by
38      * the Framework and given out to applications as tokens to be used to identify
39      * the request.
40      * @hide
41      */
42     public final int requestId;
43 
44     /**
45      * Set for legacy requests and the default.  Set to TYPE_NONE for none.
46      * Causes CONNECTIVITY_ACTION broadcasts to be sent.
47      * @hide
48      */
49     public final int legacyType;
50 
51     /**
52      * A NetworkRequest as used by the system can be one of the following types:
53      *
54      *     - LISTEN, for which the framework will issue callbacks about any
55      *       and all networks that match the specified NetworkCapabilities,
56      *
57      *     - REQUEST, capable of causing a specific network to be created
58      *       first (e.g. a telephony DUN request), the framework will issue
59      *       callbacks about the single, highest scoring current network
60      *       (if any) that matches the specified NetworkCapabilities, or
61      *
62      *     - TRACK_DEFAULT, a hybrid of the two designed such that the
63      *       framework will issue callbacks for the single, highest scoring
64      *       current network (if any) that matches the capabilities of the
65      *       default Internet request (mDefaultRequest), but which cannot cause
66      *       the framework to either create or retain the existence of any
67      *       specific network. Note that from the point of view of the request
68      *       matching code, TRACK_DEFAULT is identical to REQUEST: its special
69      *       behaviour is not due to different semantics, but to the fact that
70      *       the system will only ever create a TRACK_DEFAULT with capabilities
71      *       that are identical to the default request's capabilities, thus
72      *       causing it to share fate in every way with the default request.
73      *
74      *     - BACKGROUND_REQUEST, like REQUEST but does not cause any networks
75      *       to retain the NET_CAPABILITY_FOREGROUND capability. A network with
76      *       no foreground requests is in the background. A network that has
77      *       one or more background requests and loses its last foreground
78      *       request to a higher-scoring network will not go into the
79      *       background immediately, but will linger and go into the background
80      *       after the linger timeout.
81      *
82      *     - The value NONE is used only by applications. When an application
83      *       creates a NetworkRequest, it does not have a type; the type is set
84      *       by the system depending on the method used to file the request
85      *       (requestNetwork, registerNetworkCallback, etc.).
86      *
87      * @hide
88      */
89     public static enum Type {
90         NONE,
91         LISTEN,
92         TRACK_DEFAULT,
93         REQUEST,
94         BACKGROUND_REQUEST,
95     };
96 
97     /**
98      * The type of the request. This is only used by the system and is always NONE elsewhere.
99      *
100      * @hide
101      */
102     public final Type type;
103 
104     /**
105      * @hide
106      */
NetworkRequest(NetworkCapabilities nc, int legacyType, int rId, Type type)107     public NetworkRequest(NetworkCapabilities nc, int legacyType, int rId, Type type) {
108         if (nc == null) {
109             throw new NullPointerException();
110         }
111         requestId = rId;
112         networkCapabilities = nc;
113         this.legacyType = legacyType;
114         this.type = type;
115     }
116 
117     /**
118      * @hide
119      */
NetworkRequest(NetworkRequest that)120     public NetworkRequest(NetworkRequest that) {
121         networkCapabilities = new NetworkCapabilities(that.networkCapabilities);
122         requestId = that.requestId;
123         this.legacyType = that.legacyType;
124         this.type = that.type;
125     }
126 
127     /**
128      * Builder used to create {@link NetworkRequest} objects.  Specify the Network features
129      * needed in terms of {@link NetworkCapabilities} features
130      */
131     public static class Builder {
132         private final NetworkCapabilities mNetworkCapabilities = new NetworkCapabilities();
133 
134         /**
135          * Default constructor for Builder.
136          */
Builder()137         public Builder() {}
138 
139         /**
140          * Build {@link NetworkRequest} give the current set of capabilities.
141          */
build()142         public NetworkRequest build() {
143             // Make a copy of mNetworkCapabilities so we don't inadvertently remove NOT_RESTRICTED
144             // when later an unrestricted capability could be added to mNetworkCapabilities, in
145             // which case NOT_RESTRICTED should be returned to mNetworkCapabilities, which
146             // maybeMarkCapabilitiesRestricted() doesn't add back.
147             final NetworkCapabilities nc = new NetworkCapabilities(mNetworkCapabilities);
148             nc.maybeMarkCapabilitiesRestricted();
149             return new NetworkRequest(nc, ConnectivityManager.TYPE_NONE,
150                     ConnectivityManager.REQUEST_ID_UNSET, Type.NONE);
151         }
152 
153         /**
154          * Add the given capability requirement to this builder.  These represent
155          * the requested network's required capabilities.  Note that when searching
156          * for a network to satisfy a request, all capabilities requested must be
157          * satisfied.  See {@link NetworkCapabilities} for {@code NET_CAPABILITY_*}
158          * definitions.
159          *
160          * @param capability The {@code NetworkCapabilities.NET_CAPABILITY_*} to add.
161          * @return The builder to facilitate chaining
162          *         {@code builder.addCapability(...).addCapability();}.
163          */
addCapability(int capability)164         public Builder addCapability(int capability) {
165             mNetworkCapabilities.addCapability(capability);
166             return this;
167         }
168 
169         /**
170          * Removes (if found) the given capability from this builder instance.
171          *
172          * @param capability The {@code NetworkCapabilities.NET_CAPABILITY_*} to remove.
173          * @return The builder to facilitate chaining.
174          */
removeCapability(int capability)175         public Builder removeCapability(int capability) {
176             mNetworkCapabilities.removeCapability(capability);
177             return this;
178         }
179 
180         /**
181          * Completely clears all the {@code NetworkCapabilities} from this builder instance,
182          * removing even the capabilities that are set by default when the object is constructed.
183          *
184          * @return The builder to facilitate chaining.
185          * @hide
186          */
clearCapabilities()187         public Builder clearCapabilities() {
188             mNetworkCapabilities.clearAll();
189             return this;
190         }
191 
192         /**
193          * Adds the given transport requirement to this builder.  These represent
194          * the set of allowed transports for the request.  Only networks using one
195          * of these transports will satisfy the request.  If no particular transports
196          * are required, none should be specified here.  See {@link NetworkCapabilities}
197          * for {@code TRANSPORT_*} definitions.
198          *
199          * @param transportType The {@code NetworkCapabilities.TRANSPORT_*} to add.
200          * @return The builder to facilitate chaining.
201          */
addTransportType(int transportType)202         public Builder addTransportType(int transportType) {
203             mNetworkCapabilities.addTransportType(transportType);
204             return this;
205         }
206 
207         /**
208          * Removes (if found) the given transport from this builder instance.
209          *
210          * @param transportType The {@code NetworkCapabilities.TRANSPORT_*} to remove.
211          * @return The builder to facilitate chaining.
212          */
removeTransportType(int transportType)213         public Builder removeTransportType(int transportType) {
214             mNetworkCapabilities.removeTransportType(transportType);
215             return this;
216         }
217 
218         /**
219          * @hide
220          */
setLinkUpstreamBandwidthKbps(int upKbps)221         public Builder setLinkUpstreamBandwidthKbps(int upKbps) {
222             mNetworkCapabilities.setLinkUpstreamBandwidthKbps(upKbps);
223             return this;
224         }
225         /**
226          * @hide
227          */
setLinkDownstreamBandwidthKbps(int downKbps)228         public Builder setLinkDownstreamBandwidthKbps(int downKbps) {
229             mNetworkCapabilities.setLinkDownstreamBandwidthKbps(downKbps);
230             return this;
231         }
232 
233         /**
234          * Sets the optional bearer specific network specifier.
235          * This has no meaning if a single transport is also not specified, so calling
236          * this without a single transport set will generate an exception, as will
237          * subsequently adding or removing transports after this is set.
238          * </p>
239          * The interpretation of this {@code String} is bearer specific and bearers that use
240          * it should document their particulars.  For example, Bluetooth may use some sort of
241          * device id while WiFi could used ssid and/or bssid.  Cellular may use carrier spn.
242          *
243          * @param networkSpecifier An {@code String} of opaque format used to specify the bearer
244          *                         specific network specifier where the bearer has a choice of
245          *                         networks.
246          */
setNetworkSpecifier(String networkSpecifier)247         public Builder setNetworkSpecifier(String networkSpecifier) {
248             if (NetworkCapabilities.MATCH_ALL_REQUESTS_NETWORK_SPECIFIER.equals(networkSpecifier)) {
249                 throw new IllegalArgumentException("Invalid network specifier - must not be '"
250                         + NetworkCapabilities.MATCH_ALL_REQUESTS_NETWORK_SPECIFIER + "'");
251             }
252             mNetworkCapabilities.setNetworkSpecifier(networkSpecifier);
253             return this;
254         }
255 
256         /**
257          * Sets the signal strength. This is a signed integer, with higher values indicating a
258          * stronger signal. The exact units are bearer-dependent. For example, Wi-Fi uses the same
259          * RSSI units reported by WifiManager.
260          * <p>
261          * Note that when used to register a network callback, this specifies the minimum acceptable
262          * signal strength. When received as the state of an existing network it specifies the
263          * current value. A value of {@code SIGNAL_STRENGTH_UNSPECIFIED} means no value when
264          * received and has no effect when requesting a callback.
265          *
266          * @param signalStrength the bearer-specific signal strength.
267          * @hide
268          */
setSignalStrength(int signalStrength)269         public Builder setSignalStrength(int signalStrength) {
270             mNetworkCapabilities.setSignalStrength(signalStrength);
271             return this;
272         }
273     }
274 
275     // implement the Parcelable interface
describeContents()276     public int describeContents() {
277         return 0;
278     }
writeToParcel(Parcel dest, int flags)279     public void writeToParcel(Parcel dest, int flags) {
280         dest.writeParcelable(networkCapabilities, flags);
281         dest.writeInt(legacyType);
282         dest.writeInt(requestId);
283         dest.writeString(type.name());
284     }
285     public static final Creator<NetworkRequest> CREATOR =
286         new Creator<NetworkRequest>() {
287             public NetworkRequest createFromParcel(Parcel in) {
288                 NetworkCapabilities nc = (NetworkCapabilities)in.readParcelable(null);
289                 int legacyType = in.readInt();
290                 int requestId = in.readInt();
291                 Type type = Type.valueOf(in.readString());  // IllegalArgumentException if invalid.
292                 NetworkRequest result = new NetworkRequest(nc, legacyType, requestId, type);
293                 return result;
294             }
295             public NetworkRequest[] newArray(int size) {
296                 return new NetworkRequest[size];
297             }
298         };
299 
300     /**
301      * Returns true iff. this NetworkRequest is of type LISTEN.
302      *
303      * @hide
304      */
isListen()305     public boolean isListen() {
306         return type == Type.LISTEN;
307     }
308 
309     /**
310      * Returns true iff. the contained NetworkRequest is one that:
311      *
312      *     - should be associated with at most one satisfying network
313      *       at a time;
314      *
315      *     - should cause a network to be kept up, but not necessarily in
316      *       the foreground, if it is the best network which can satisfy the
317      *       NetworkRequest.
318      *
319      * For full detail of how isRequest() is used for pairing Networks with
320      * NetworkRequests read rematchNetworkAndRequests().
321      *
322      * @hide
323      */
isRequest()324     public boolean isRequest() {
325         return isForegroundRequest() || isBackgroundRequest();
326     }
327 
328     /**
329      * Returns true iff. the contained NetworkRequest is one that:
330      *
331      *     - should be associated with at most one satisfying network
332      *       at a time;
333      *
334      *     - should cause a network to be kept up and in the foreground if
335      *       it is the best network which can satisfy the NetworkRequest.
336      *
337      * For full detail of how isRequest() is used for pairing Networks with
338      * NetworkRequests read rematchNetworkAndRequests().
339      *
340      * @hide
341      */
isForegroundRequest()342     public boolean isForegroundRequest() {
343         return type == Type.TRACK_DEFAULT || type == Type.REQUEST;
344     }
345 
346     /**
347      * Returns true iff. this NetworkRequest is of type BACKGROUND_REQUEST.
348      *
349      * @hide
350      */
isBackgroundRequest()351     public boolean isBackgroundRequest() {
352         return type == Type.BACKGROUND_REQUEST;
353     }
354 
toString()355     public String toString() {
356         return "NetworkRequest [ " + type + " id=" + requestId +
357                 (legacyType != ConnectivityManager.TYPE_NONE ? ", legacyType=" + legacyType : "") +
358                 ", " + networkCapabilities.toString() + " ]";
359     }
360 
equals(Object obj)361     public boolean equals(Object obj) {
362         if (obj instanceof NetworkRequest == false) return false;
363         NetworkRequest that = (NetworkRequest)obj;
364         return (that.legacyType == this.legacyType &&
365                 that.requestId == this.requestId &&
366                 that.type == this.type &&
367                 Objects.equals(that.networkCapabilities, this.networkCapabilities));
368     }
369 
hashCode()370     public int hashCode() {
371         return Objects.hash(requestId, legacyType, networkCapabilities, type);
372     }
373 }
374