340 lines
13 KiB
Java
340 lines
13 KiB
Java
// Copyright 2016 The Chromium Authors
|
|
// Use of this source code is governed by a BSD-style license that can be
|
|
// found in the LICENSE file.
|
|
|
|
package org.chromium.net;
|
|
|
|
import androidx.annotation.Nullable;
|
|
|
|
import java.util.Collection;
|
|
import java.util.Date;
|
|
import java.util.concurrent.Executor;
|
|
|
|
/**
|
|
* Information about a finished request. Passed to {@link RequestFinishedInfo.Listener}.
|
|
*
|
|
* <p>To associate the data with the original request, use {@link
|
|
* UrlRequest.Builder#addRequestAnnotation} to add a unique identifier when creating the
|
|
* request, and call {@link #getAnnotations} when the {@link RequestFinishedInfo} is received to
|
|
* retrieve the identifier.
|
|
*/
|
|
public abstract class RequestFinishedInfo {
|
|
/** Listens for finished requests for the purpose of collecting metrics. */
|
|
public abstract static class Listener {
|
|
private final Executor mExecutor;
|
|
|
|
public Listener(Executor executor) {
|
|
if (executor == null) {
|
|
throw new IllegalStateException("Executor must not be null");
|
|
}
|
|
mExecutor = executor;
|
|
}
|
|
|
|
/**
|
|
* Invoked with request info. Will be called in a task submitted to the {@link
|
|
* java.util.concurrent.Executor} returned by {@link #getExecutor}.
|
|
*
|
|
* @param requestInfo {@link RequestFinishedInfo} for finished request.
|
|
*/
|
|
public abstract void onRequestFinished(RequestFinishedInfo requestInfo);
|
|
|
|
/**
|
|
* Returns this listener's executor. Can be called on any thread.
|
|
*
|
|
* @return this listener's {@link java.util.concurrent.Executor}
|
|
*/
|
|
public Executor getExecutor() {
|
|
return mExecutor;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Metrics collected for a single request. Most of these metrics are timestamps for events
|
|
* during the lifetime of the request, which can be used to build a detailed timeline for
|
|
* investigating performance.
|
|
*
|
|
* <p>Events happen in this order:
|
|
*
|
|
* <ol>
|
|
* <li>{@link #getRequestStart request start}
|
|
* <li>{@link #getDnsStart DNS start}
|
|
* <li>{@link #getDnsEnd DNS end}
|
|
* <li>{@link #getConnectStart connect start}
|
|
* <li>{@link #getSslStart SSL start}
|
|
* <li>{@link #getSslEnd SSL end}
|
|
* <li>{@link #getConnectEnd connect end}
|
|
* <li>{@link #getSendingStart sending start}
|
|
* <li>{@link #getSendingEnd sending end}
|
|
* <li>{@link #getResponseStart response start}
|
|
* <li>{@link #getRequestEnd request end}
|
|
* </ol>
|
|
*
|
|
* Start times are reported as the time when a request started blocking on event, not when the
|
|
* event actually occurred, with the exception of push start and end. If a metric is not
|
|
* meaningful or not available, including cases when a request finished before reaching that
|
|
* stage, start and end times will be {@code null}. If no time was spent blocking on an event,
|
|
* start and end will be the same time.
|
|
*
|
|
* <p>If the system clock is adjusted during the request, some of the {@link java.util.Date}
|
|
* values might not match it. Timestamps are recorded using a clock that is guaranteed not to
|
|
* run backwards. All timestamps are correct relative to the system clock at the time of request
|
|
* start, and taking the difference between two timestamps will give the correct difference
|
|
* between the events. In order to preserve this property, timestamps for events other than
|
|
* request start are not guaranteed to match the system clock at the times they represent.
|
|
*
|
|
* <p>Most timing metrics are taken from <a
|
|
* href="https://cs.chromium.org/chromium/src/net/base/load_timing_info.h">LoadTimingInfo</a>,
|
|
* which holds the information for <a href="http://w3c.github.io/navigation-timing/"></a> and <a
|
|
* href="https://www.w3.org/TR/resource-timing/"></a>.
|
|
*
|
|
* <p>{@hide} as it's a prototype.
|
|
*/
|
|
public abstract static class Metrics {
|
|
/**
|
|
* Returns time when the request started.
|
|
*
|
|
* @return {@link java.util.Date} representing when the native request actually started.
|
|
* This
|
|
* timestamp will match the system clock at the time it represents.
|
|
*/
|
|
@Nullable
|
|
public abstract Date getRequestStart();
|
|
|
|
/**
|
|
* Returns time when DNS lookup started. This and {@link #getDnsEnd} will return non-null
|
|
* values regardless of whether the result came from a DNS server or the local cache.
|
|
*
|
|
* @return {@link java.util.Date} representing when DNS lookup started. {@code null} if the
|
|
* socket was reused (see {@link #getSocketReused}).
|
|
*/
|
|
@Nullable
|
|
public abstract Date getDnsStart();
|
|
|
|
/**
|
|
* Returns time when DNS lookup finished. This and {@link #getDnsStart} will return non-null
|
|
* values regardless of whether the result came from a DNS server or the local cache.
|
|
*
|
|
* @return {@link java.util.Date} representing when DNS lookup finished. {@code null} if the
|
|
* socket was reused (see {@link #getSocketReused}).
|
|
*/
|
|
@Nullable
|
|
public abstract Date getDnsEnd();
|
|
|
|
/**
|
|
* Returns time when connection establishment started.
|
|
*
|
|
* @return {@link java.util.Date} representing when connection establishment started,
|
|
* typically
|
|
* when DNS resolution finishes. {@code null} if the socket was reused (see {@link
|
|
* #getSocketReused}).
|
|
*/
|
|
@Nullable
|
|
public abstract Date getConnectStart();
|
|
|
|
/**
|
|
* Returns time when connection establishment finished.
|
|
*
|
|
* @return {@link java.util.Date} representing when connection establishment finished, after
|
|
* TCP
|
|
* connection is established and, if using HTTPS, SSL handshake is completed. For QUIC
|
|
* 0-RTT, this represents the time of handshake confirmation and might happen later than
|
|
* {@link #getSendingStart}. {@code null} if the socket was reused (see {@link
|
|
* #getSocketReused}).
|
|
*/
|
|
@Nullable
|
|
public abstract Date getConnectEnd();
|
|
|
|
/**
|
|
* Returns time when SSL handshake started. For QUIC, this will be the same time as {@link
|
|
* #getConnectStart}.
|
|
*
|
|
* @return {@link java.util.Date} representing when SSL handshake started. {@code null} if
|
|
* SSL
|
|
* is not used or if the socket was reused (see {@link #getSocketReused}).
|
|
*/
|
|
@Nullable
|
|
public abstract Date getSslStart();
|
|
|
|
/**
|
|
* Returns time when SSL handshake finished. For QUIC, this will be the same time as {@link
|
|
* #getConnectEnd}.
|
|
*
|
|
* @return {@link java.util.Date} representing when SSL handshake finished. {@code null} if
|
|
* SSL
|
|
* is not used or if the socket was reused (see {@link #getSocketReused}).
|
|
*/
|
|
@Nullable
|
|
public abstract Date getSslEnd();
|
|
|
|
/**
|
|
* Returns time when sending the request started.
|
|
*
|
|
* @return {@link java.util.Date} representing when sending HTTP request headers started.
|
|
*/
|
|
@Nullable
|
|
public abstract Date getSendingStart();
|
|
|
|
/**
|
|
* Returns time when sending the request finished.
|
|
*
|
|
* @return {@link java.util.Date} representing when sending HTTP request body finished.
|
|
* (Sending
|
|
* request body happens after sending request headers.)
|
|
*/
|
|
@Nullable
|
|
public abstract Date getSendingEnd();
|
|
|
|
/**
|
|
* Returns time when first byte of HTTP/2 server push was received.
|
|
*
|
|
* @return {@link java.util.Date} representing when the first byte of an HTTP/2 server push
|
|
* was
|
|
* received. {@code null} if server push is not used.
|
|
*/
|
|
@Nullable
|
|
public abstract Date getPushStart();
|
|
|
|
/**
|
|
* Returns time when last byte of HTTP/2 server push was received.
|
|
*
|
|
* @return {@link java.util.Date} representing when the last byte of an HTTP/2 server push
|
|
* was
|
|
* received. {@code null} if server push is not used.
|
|
*/
|
|
@Nullable
|
|
public abstract Date getPushEnd();
|
|
|
|
/**
|
|
* Returns time when the end of the response headers was received.
|
|
*
|
|
* @return {@link java.util.Date} representing when the end of the response headers was
|
|
* received.
|
|
*/
|
|
@Nullable
|
|
public abstract Date getResponseStart();
|
|
|
|
/**
|
|
* Returns time when the request finished.
|
|
*
|
|
* @return {@link java.util.Date} representing when the request finished.
|
|
*/
|
|
@Nullable
|
|
public abstract Date getRequestEnd();
|
|
|
|
/**
|
|
* Returns whether the socket was reused from a previous request. In HTTP/2 or QUIC, if
|
|
* streams are multiplexed in a single connection, returns {@code true} for all streams
|
|
* after the first.
|
|
*
|
|
* @return whether this request reused a socket from a previous request. When {@code true},
|
|
* DNS,
|
|
* connection, and SSL times will be {@code null}.
|
|
*/
|
|
public abstract boolean getSocketReused();
|
|
|
|
/**
|
|
* Returns milliseconds between request initiation and first byte of response headers, or
|
|
* {@code null} if not collected. TODO(mgersh): Remove once new API works
|
|
* http://crbug.com/629194
|
|
* {@hide}
|
|
*/
|
|
@Nullable
|
|
public abstract Long getTtfbMs();
|
|
|
|
/**
|
|
* Returns milliseconds between request initiation and finish, including a failure or
|
|
* cancellation, or {@code null} if not collected. TODO(mgersh): Remove once new API works
|
|
* http://crbug.com/629194 {@hide}
|
|
*/
|
|
@Nullable
|
|
public abstract Long getTotalTimeMs();
|
|
|
|
/**
|
|
* Returns total bytes sent over the network transport layer, or {@code null} if not
|
|
* collected.
|
|
*/
|
|
@Nullable
|
|
public abstract Long getSentByteCount();
|
|
|
|
/**
|
|
* Returns total bytes received over the network transport layer, or {@code null} if not
|
|
* collected. Number of bytes does not include any previous redirects.
|
|
*/
|
|
@Nullable
|
|
public abstract Long getReceivedByteCount();
|
|
}
|
|
|
|
/** Reason value indicating that the request succeeded. Returned from {@link #getFinishedReason}. */
|
|
public static final int SUCCEEDED = 0;
|
|
|
|
/**
|
|
* Reason value indicating that the request failed or returned an error. Returned from {@link
|
|
* #getFinishedReason}.
|
|
*/
|
|
public static final int FAILED = 1;
|
|
|
|
/**
|
|
* Reason value indicating that the request was canceled. Returned from {@link
|
|
* #getFinishedReason}.
|
|
*/
|
|
public static final int CANCELED = 2;
|
|
|
|
/**
|
|
* Returns the request's original URL.
|
|
*
|
|
* @return the request's original URL
|
|
*/
|
|
public abstract String getUrl();
|
|
|
|
/**
|
|
* Returns the objects that the caller has supplied when initiating the request, using {@link
|
|
* UrlRequest.Builder#addRequestAnnotation}. Annotations can be used to associate a
|
|
* {@link RequestFinishedInfo} with the original request or type of request.
|
|
*
|
|
* @return annotations supplied when creating the request
|
|
*/
|
|
public abstract Collection<Object> getAnnotations();
|
|
|
|
// TODO(klm): Collect and return a chain of Metrics objects for redirect responses.
|
|
// TODO(mgersh): Update this javadoc when new metrics are fully implemented
|
|
|
|
/**
|
|
* Returns metrics collected for this request.
|
|
*
|
|
* <p>The reported times and bytes account for all redirects, i.e.
|
|
* the TTFB is from the start of the original request to the ultimate response headers, the TTLB
|
|
* is from the start of the original request to the end of the ultimate response, the received
|
|
* byte count is for all redirects and the ultimate response combined. These cumulative metric
|
|
* definitions are debatable, but are chosen to make sense for user-facing latency analysis.
|
|
*
|
|
* @return metrics collected for this request.
|
|
*
|
|
* <p>{@hide} as the Metrics class is hidden
|
|
*/
|
|
public abstract Metrics getMetrics();
|
|
|
|
/**
|
|
* Returns the reason why the request finished.
|
|
*
|
|
* @return one of {@link #SUCCEEDED}, {@link #FAILED}, or {@link #CANCELED}
|
|
*/
|
|
public abstract int getFinishedReason();
|
|
|
|
/**
|
|
* Returns a {@link UrlResponseInfo} for the request, if its response had started.
|
|
*
|
|
* @return {@link UrlResponseInfo} for the request, if its response had started.
|
|
*/
|
|
@Nullable
|
|
public abstract UrlResponseInfo getResponseInfo();
|
|
|
|
/**
|
|
* If the request failed, returns the same {@link CronetException} provided to {@link
|
|
* UrlRequest.Callback#onFailed}.
|
|
*
|
|
* @return the request's {@link CronetException}, if the request failed
|
|
*/
|
|
@Nullable
|
|
public abstract CronetException getException();
|
|
}
|