File: prefetch_manager.h

package info (click to toggle)
chromium 139.0.7258.127-1
  • links: PTS, VCS
  • area: main
  • in suites:
  • size: 6,122,068 kB
  • sloc: cpp: 35,100,771; ansic: 7,163,530; javascript: 4,103,002; python: 1,436,920; asm: 946,517; xml: 746,709; pascal: 187,653; perl: 88,691; sh: 88,436; objc: 79,953; sql: 51,488; cs: 44,583; fortran: 24,137; makefile: 22,147; tcl: 15,277; php: 13,980; yacc: 8,984; ruby: 7,485; awk: 3,720; lisp: 3,096; lex: 1,327; ada: 727; jsp: 228; sed: 36
file content (169 lines) | stat: -rw-r--r-- 5,538 bytes parent folder | download | duplicates (6)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
// Copyright 2020 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef CHROME_BROWSER_PREDICTORS_PREFETCH_MANAGER_H_
#define CHROME_BROWSER_PREDICTORS_PREFETCH_MANAGER_H_

#include <list>
#include <map>
#include <memory>
#include <optional>
#include <vector>

#include "base/memory/raw_ptr.h"
#include "base/memory/weak_ptr.h"
#include "base/time/time.h"
#include "chrome/browser/predictors/resource_prefetch_predictor.h"
#include "net/base/network_anonymization_key.h"
#include "services/network/public/mojom/fetch_api.mojom-forward.h"
#include "services/network/public/mojom/url_loader.mojom-forward.h"
#include "third_party/blink/public/mojom/loader/resource_load_info.mojom-forward.h"
#include "url/gurl.h"

class Profile;

namespace blink {
class ThrottlingURLLoader;
}

namespace network {
namespace mojom {
class URLLoaderClient;
}
class SharedURLLoaderFactory;
struct URLLoaderCompletionStatus;
}

namespace predictors {

struct PrefetchRequest;
struct PrefetchInfo;
struct PrefetchJob;

inline constexpr size_t kMaxInflightPrefetches = 3;

struct PrefetchStats {
  explicit PrefetchStats(const GURL& url);
  ~PrefetchStats();

  PrefetchStats(const PrefetchStats&) = delete;
  PrefetchStats& operator=(const PrefetchStats&) = delete;

  GURL url;
  base::TimeTicks start_time;
  // TODO(falken): Add stats about what was requested to measure
  // the accuracy.
};

// PrefetchManager prefetches input lists of URLs.
//  - The input list of URLs is associated with a main frame url that can be
//  used for cancelling.
//  - Limits the total number of prefetches in flight.
//  - All methods of the class must be called on the UI thread.
//
//  This class is very similar to PreconnectManager, which does
//  preresolve/preconnect instead of prefetching. It is only
//  usable when LoadingPredictorPrefetch is enabled.
class PrefetchManager {
 public:
  // Delegate methods are not called when the
  // kPrefetchManagerUseNetworkContextPrefetch feature is enabled, as this class
  // does not track progress in that case.
  class Delegate {
   public:
    virtual ~Delegate() = default;

    // Called when a prefetch is initiated. |prefetch_url| is the subresource
    // being prefetched, and |url| is the main frame of the navigation.
    virtual void PrefetchInitiated(const GURL& url,
                                   const GURL& prefetch_url) = 0;

    // Called when all prefetch jobs for the |stats->url| are finished.
    // Called on the UI thread.
    virtual void PrefetchFinished(std::unique_ptr<PrefetchStats> stats) = 0;
  };

  // For testing. Observer methods will not be called when the
  // kPrefetchManagerUseNetworkContextPrefetch feature is enabled.
  class Observer {
   public:
    virtual ~Observer() = default;

    virtual void OnPrefetchFinished(
        const GURL& url,
        const GURL& prefetch_url,
        const network::URLLoaderCompletionStatus& status) {}
    virtual void OnAllPrefetchesFinished(const GURL& url) {}
  };

  PrefetchManager(base::WeakPtr<Delegate> delegate, Profile* profile);
  ~PrefetchManager();

  PrefetchManager(const PrefetchManager&) = delete;
  PrefetchManager& operator=(const PrefetchManager&) = delete;

  static bool IsAvailableForPrefetch(
      network::mojom::RequestDestination destination);

  // Starts prefetch jobs keyed by |url|.
  void Start(const GURL& url, std::vector<PrefetchRequest> requests);

  // Stops further prefetch jobs keyed by |url|. Queued jobs will never start;
  // started jobs will continue to completion.
  void Stop(const GURL& url);

  base::WeakPtr<PrefetchManager> GetWeakPtr() {
    return weak_factory_.GetWeakPtr();
  }

  // Called by PrefetchInfo.
  void AllPrefetchJobsForUrlFinished(PrefetchInfo& info);

  void set_observer_for_testing(Observer* observer) {
    observer_for_testing_ = observer;
  }

 private:
  friend class PrefetchManagerTest;

  void PrefetchUrl(std::unique_ptr<PrefetchJob> job,
                   scoped_refptr<network::SharedURLLoaderFactory> factory);
  void OnPrefetchFinished(
      std::unique_ptr<PrefetchJob> job,
      std::unique_ptr<blink::ThrottlingURLLoader> loader,
      std::unique_ptr<network::mojom::URLLoaderClient> client,
      const network::URLLoaderCompletionStatus& status);
  void TryToLaunchPrefetchJobs();

  base::WeakPtr<Delegate> delegate_;
  const raw_ptr<Profile, DanglingUntriaged> profile_;

  // All the jobs that haven't yet started. A job is removed once it starts.
  // Inflight jobs destruct once finished.
  std::list<std::unique_ptr<PrefetchJob>> queued_jobs_;

  std::map<GURL, std::unique_ptr<PrefetchInfo>> prefetch_info_;

  // The total number of prefetches that have started and not yet finished,
  // across all main frame URLs.
  size_t inflight_jobs_count_ = 0;

  raw_ptr<Observer, DanglingUntriaged> observer_for_testing_ = nullptr;

  // True if the feature "PrefetchManagerUseNetworkContextPrefetch" is in use,
  // in which case this class just fires off prefetches but does not track their
  // completion.
  const bool use_network_context_prefetch_;

  base::WeakPtrFactory<PrefetchManager> weak_factory_{this};
};

// Returns a relevant ResourceType for the given RequestDestination if it's
// supported by prefetch. Otherwise, returns nullopt.
std::optional<blink::mojom::ResourceType> GetResourceTypeForPrefetch(
    network::mojom::RequestDestination destination);

}  // namespace predictors

#endif  // CHROME_BROWSER_PREDICTORS_PREFETCH_MANAGER_H_