Bug 1879011 - Fix openFirefoxSuggestSponsoredSearchResultsTest UI test r=ohorvath
[gecko.git] / netwerk / base / SimpleChannel.h
blobd469adf65d530146421c3e3f0f19c26c77b3f348
1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* This Source Code Form is subject to the terms of the Mozilla Public
3 * License, v. 2.0. If a copy of the MPL was not distributed with this
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 #ifndef SimpleChannel_h
7 #define SimpleChannel_h
9 #include "mozilla/ResultExtensions.h"
10 #include "mozilla/UniquePtr.h"
11 #include "nsBaseChannel.h"
12 #include "nsIChildChannel.h"
13 #include "mozilla/net/PSimpleChannelChild.h"
14 #include "nsCOMPtr.h"
16 class nsIChannel;
17 class nsIInputStream;
18 class nsILoadInfo;
19 class nsIRequest;
20 class nsIStreamListener;
21 class nsIURI;
23 //-----------------------------------------------------------------------------
25 namespace mozilla {
27 using InputStreamOrReason = Result<nsCOMPtr<nsIInputStream>, nsresult>;
28 using NotNullRequest = NotNull<nsCOMPtr<nsIRequest>>;
29 using NotNullCancelable = NotNull<nsCOMPtr<nsICancelable>>;
30 using RequestOrCancelable = Variant<NotNullRequest, NotNullCancelable>;
31 using RequestOrReason = Result<RequestOrCancelable, nsresult>;
33 namespace net {
35 class SimpleChannelCallbacks {
36 public:
37 virtual InputStreamOrReason OpenContentStream(bool async,
38 nsIChannel* channel) = 0;
40 virtual RequestOrReason StartAsyncRead(nsIStreamListener* stream,
41 nsIChannel* channel) = 0;
43 virtual ~SimpleChannelCallbacks() = default;
46 template <typename F1, typename F2, typename T>
47 class SimpleChannelCallbacksImpl final : public SimpleChannelCallbacks {
48 public:
49 SimpleChannelCallbacksImpl(F1&& aStartAsyncRead, F2&& aOpenContentStream,
50 T* context)
51 : mStartAsyncRead(aStartAsyncRead),
52 mOpenContentStream(aOpenContentStream),
53 mContext(context) {}
55 virtual ~SimpleChannelCallbacksImpl() = default;
57 virtual InputStreamOrReason OpenContentStream(bool async,
58 nsIChannel* channel) override {
59 return mOpenContentStream(async, channel, mContext);
62 virtual RequestOrReason StartAsyncRead(nsIStreamListener* listener,
63 nsIChannel* channel) override {
64 return mStartAsyncRead(listener, channel, mContext);
67 private:
68 F1 mStartAsyncRead;
69 F2 mOpenContentStream;
70 RefPtr<T> mContext;
73 class SimpleChannel : public nsBaseChannel {
74 public:
75 explicit SimpleChannel(UniquePtr<SimpleChannelCallbacks>&& aCallbacks);
77 protected:
78 virtual ~SimpleChannel() = default;
80 virtual nsresult OpenContentStream(bool async, nsIInputStream** streamOut,
81 nsIChannel** channel) override;
83 virtual nsresult BeginAsyncRead(nsIStreamListener* listener,
84 nsIRequest** request,
85 nsICancelable** cancelableRequest) override;
87 private:
88 UniquePtr<SimpleChannelCallbacks> mCallbacks;
91 class SimpleChannelChild final : public SimpleChannel,
92 public nsIChildChannel,
93 public PSimpleChannelChild {
94 public:
95 explicit SimpleChannelChild(UniquePtr<SimpleChannelCallbacks>&& aCallbacks);
97 NS_DECL_ISUPPORTS_INHERITED
98 NS_DECL_NSICHILDCHANNEL
100 private:
101 virtual ~SimpleChannelChild() = default;
104 already_AddRefed<nsIChannel> NS_NewSimpleChannelInternal(
105 nsIURI* aURI, nsILoadInfo* aLoadInfo,
106 UniquePtr<SimpleChannelCallbacks>&& aCallbacks);
108 } // namespace net
109 } // namespace mozilla
112 * Creates a simple channel which wraps an input stream created by the given
113 * callbacks. The callbacks are not called until the underlying AsyncOpen or
114 * Open methods are called, and correspond to the nsBaseChannel::StartAsyncRead
115 * and nsBaseChannel::OpenContentStream methods of the same names.
117 * The last two arguments of each callback are the created channel instance,
118 * and the ref-counted context object passed to NS_NewSimpleChannel. A strong
119 * reference to that object is guaranteed to be kept alive until after a
120 * callback successfully completes.
122 template <typename T, typename F1, typename F2>
123 inline already_AddRefed<nsIChannel> NS_NewSimpleChannel(
124 nsIURI* aURI, nsILoadInfo* aLoadInfo, T* context, F1&& aStartAsyncRead,
125 F2&& aOpenContentStream) {
126 using namespace mozilla;
128 auto callbacks = MakeUnique<net::SimpleChannelCallbacksImpl<F1, F2, T>>(
129 std::forward<F1>(aStartAsyncRead), std::forward<F2>(aOpenContentStream),
130 context);
132 return net::NS_NewSimpleChannelInternal(aURI, aLoadInfo,
133 std::move(callbacks));
136 template <typename T, typename F1>
137 inline already_AddRefed<nsIChannel> NS_NewSimpleChannel(nsIURI* aURI,
138 nsILoadInfo* aLoadInfo,
139 T* context,
140 F1&& aStartAsyncRead) {
141 using namespace mozilla;
143 auto openContentStream = [](bool async, nsIChannel* channel, T* context) {
144 return Err(NS_ERROR_NOT_IMPLEMENTED);
147 return NS_NewSimpleChannel(aURI, aLoadInfo, context,
148 std::forward<F1>(aStartAsyncRead),
149 std::move(openContentStream));
152 #endif // SimpleChannel_h