rippled
Loading...
Searching...
No Matches
GRPCServer.h
1//------------------------------------------------------------------------------
2/*
3 This file is part of rippled: https://github.com/ripple/rippled
4 Copyright (c) 2012, 2013 Ripple Labs Inc.
5
6 Permission to use, copy, modify, and/or distribute this software for any
7 purpose with or without fee is hereby granted, provided that the above
8 copyright notice and this permission notice appear in all copies.
9
10 THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11 WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12 MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13 ANY SPECIAL , DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14 WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15 ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16 OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17*/
18//==============================================================================
19
20#ifndef RIPPLE_CORE_GRPCSERVER_H_INCLUDED
21#define RIPPLE_CORE_GRPCSERVER_H_INCLUDED
22
23#include <xrpld/app/main/Application.h>
24#include <xrpld/core/JobQueue.h>
25#include <xrpld/rpc/Context.h>
26#include <xrpld/rpc/GRPCHandlers.h>
27#include <xrpld/rpc/InfoSub.h>
28#include <xrpld/rpc/Role.h>
29#include <xrpld/rpc/detail/Handler.h>
30
31#include <xrpl/proto/org/xrpl/rpc/v1/xrp_ledger.grpc.pb.h>
32#include <xrpl/resource/Charge.h>
33
34#include <grpcpp/grpcpp.h>
35
36namespace ripple {
37
38// Interface that CallData implements
40{
41public:
42 virtual ~Processor() = default;
43
44 Processor() = default;
45
46 Processor(Processor const&) = delete;
47
49 operator=(Processor const&) = delete;
50
51 // process a request that has arrived. Can only be called once per instance
52 virtual void
53 process() = 0;
54
55 // create a new instance of this CallData object, with the same type
56 //(same template parameters) as original. This is called when a CallData
57 // object starts processing a request. Creating a new instance allows the
58 // server to handle additional requests while the first is being processed
60 clone() = 0;
61
62 // true if this object has finished processing the request. Object will be
63 // deleted once this function returns true
64 virtual bool
66};
67
68class GRPCServerImpl final
69{
70private:
71 // CompletionQueue returns events that have occurred, or events that have
72 // been cancelled
74
76
77 // The gRPC service defined by the .proto files
78 org::xrpl::rpc::v1::XRPLedgerAPIService::AsyncService service_;
79
81
83
86
88
90
91 // typedef for function to bind a listener
92 // This is always of the form:
93 // org::xrpl::rpc::v1::XRPLedgerAPIService::AsyncService::Request[RPC NAME]
94 template <class Request, class Response>
96 org::xrpl::rpc::v1::XRPLedgerAPIService::AsyncService&,
97 grpc::ServerContext*,
98 Request*,
99 grpc::ServerAsyncResponseWriter<Response>*,
100 grpc::CompletionQueue*,
101 grpc::ServerCompletionQueue*,
102 void*)>;
103
104 // typedef for actual handler (that populates a response)
105 // handlers are defined in rpc/GRPCHandlers.h
106 template <class Request, class Response>
109 // This implementation is currently limited to v1 of the API
110 static unsigned constexpr apiVersion = 1;
111
112 template <class Request, class Response>
113 using Forward = std::function<grpc::Status(
114 org::xrpl::rpc::v1::XRPLedgerAPIService::Stub*,
115 grpc::ClientContext*,
116 Request,
117 Response*)>;
118
119public:
120 explicit GRPCServerImpl(Application& app);
121
123
125 operator=(GRPCServerImpl const&) = delete;
126
127 void
128 shutdown();
129
130 // setup the server and listeners
131 // returns true if server started successfully
132 bool
133 start();
134
135 // the main event loop
136 void
137 handleRpcs();
138
139 // Create a CallData object for each RPC. Return created objects in vector
142
143 // Obtaining actually binded endpoint (if port 0 was used for server setup).
144 boost::asio::ip::tcp::endpoint
145 getEndpoint() const;
146
147private:
148 // Class encompasing the state and logic needed to serve a request.
149 template <class Request, class Response>
151 : public Processor,
152 public std::enable_shared_from_this<CallData<Request, Response>>
153 {
154 private:
155 // The means of communication with the gRPC runtime for an asynchronous
156 // server.
157 org::xrpl::rpc::v1::XRPLedgerAPIService::AsyncService& service_;
158
159 // The producer-consumer queue for asynchronous server notifications.
160 grpc::ServerCompletionQueue& cq_;
161
162 // Context for the rpc, allowing to tweak aspects of it such as the use
163 // of compression, authentication, as well as to send metadata back to
164 // the client.
165 grpc::ServerContext ctx_;
166
167 // true if finished processing request
168 // Note, this variable does not need to be atomic, since it is
169 // currently only accessed from one thread. However, isFinished(),
170 // which returns the value of this variable, is public facing. In the
171 // interest of avoiding future concurrency bugs, we make it atomic.
173
175
176 // What we get from the client.
177 Request request_;
178
179 // The means to get back to the client.
180 grpc::ServerAsyncResponseWriter<Response> responder_;
181
182 // Function that creates a listener for specific request type
184
185 // Function that processes a request
187
188 // Function to call to forward to another server
190
191 // Condition required for this RPC
193
194 // Load type for this RPC
196
198
199 public:
200 virtual ~CallData() = default;
201
202 // Take in the "service" instance (in this case representing an
203 // asynchronous server) and the completion queue "cq" used for
204 // asynchronous communication with the gRPC runtime.
205 explicit CallData(
206 org::xrpl::rpc::v1::XRPLedgerAPIService::AsyncService& service,
207 grpc::ServerCompletionQueue& cq,
208 Application& app,
212 RPC::Condition requiredCondition,
213 Resource::Charge loadType,
214 std::vector<boost::asio::ip::address> const& secureGatewayIPs);
215
216 CallData(CallData const&) = delete;
217
218 CallData&
219 operator=(CallData const&) = delete;
220
221 virtual void
222 process() override;
223
224 virtual bool
225 isFinished() override;
226
228 clone() override;
229
230 private:
231 // process the request. Called inside the coroutine passed to JobQueue
232 void
234
235 // return load type of this RPC
237 getLoadType();
238
239 // return the Role used for this RPC
240 Role
241 getRole(bool isUnlimited);
242
243 // register endpoint with ResourceManager and return usage
245 getUsage();
246
247 // Returns the ip of the client
248 // Empty optional if there was an error decoding the client ip
251
252 // Returns the endpoint of the client.
253 // Empty optional if there was an error decoding the client
254 // endpoint
257
258 // If the request was proxied through
259 // another rippled node, returns the ip of the originating client.
260 // Empty optional if request was not proxied or there was an error
261 // decoding the client ip
264
265 // If the request was proxied through
266 // another rippled node, returns the endpoint of the originating client.
267 // Empty optional if request was not proxied or there was an error
268 // decoding the client endpoint
271
272 // Returns the user specified in the request. Empty optional if no user
273 // was specified
275 getUser();
276
277 // Sets is_unlimited in response to value of clientIsUnlimited
278 // Does nothing if is_unlimited is not a field of the response
279 void
280 setIsUnlimited(Response& response, bool isUnlimited);
281
282 // True if the client is exempt from resource controls
283 bool
285
286 // True if the request was proxied through another rippled node prior
287 // to arriving here
288 bool
290
291 // forward request to a p2p node
292 void
294
295 }; // CallData
296
297}; // GRPCServerImpl
298
300{
301public:
302 explicit GRPCServer(Application& app) : impl_(app)
303 {
304 }
305
306 GRPCServer(GRPCServer const&) = delete;
307
309 operator=(GRPCServer const&) = delete;
310
311 bool
312 start();
313
314 void
315 stop();
316
317 ~GRPCServer();
318
319 boost::asio::ip::tcp::endpoint
320 getEndpoint() const;
321
322private:
325 bool running_ = false;
326};
327} // namespace ripple
328#endif
A generic endpoint for log messages.
Definition Journal.h:60
CallData(CallData const &)=delete
Forward< Request, Response > forward_
Definition GRPCServer.h:189
Resource::Consumer getUsage()
std::optional< std::string > getUser()
grpc::ServerCompletionQueue & cq_
Definition GRPCServer.h:160
Handler< Request, Response > handler_
Definition GRPCServer.h:186
CallData & operator=(CallData const &)=delete
void setIsUnlimited(Response &response, bool isUnlimited)
std::optional< boost::asio::ip::address > getClientIpAddress()
std::optional< boost::asio::ip::tcp::endpoint > getProxiedClientEndpoint()
BindListener< Request, Response > bindListener_
Definition GRPCServer.h:183
grpc::ServerAsyncResponseWriter< Response > responder_
Definition GRPCServer.h:180
Role getRole(bool isUnlimited)
std::vector< boost::asio::ip::address > const & secureGatewayIPs_
Definition GRPCServer.h:197
std::shared_ptr< Processor > clone() override
std::optional< boost::asio::ip::tcp::endpoint > getClientEndpoint()
std::optional< boost::asio::ip::address > getProxiedClientIpAddress()
org::xrpl::rpc::v1::XRPLedgerAPIService::AsyncService & service_
Definition GRPCServer.h:157
virtual void process() override
virtual bool isFinished() override
void forwardToP2p(RPC::GRPCContext< Request > &context)
std::string serverAddress_
Definition GRPCServer.h:84
Application & app_
Definition GRPCServer.h:82
std::vector< std::shared_ptr< Processor > > setupListeners()
std::unique_ptr< grpc::Server > server_
Definition GRPCServer.h:80
std::unique_ptr< grpc::ServerCompletionQueue > cq_
Definition GRPCServer.h:73
org::xrpl::rpc::v1::XRPLedgerAPIService::AsyncService service_
Definition GRPCServer.h:78
std::vector< std::shared_ptr< Processor > > requests_
Definition GRPCServer.h:75
GRPCServerImpl(GRPCServerImpl const &)=delete
GRPCServerImpl & operator=(GRPCServerImpl const &)=delete
static unsigned constexpr apiVersion
Definition GRPCServer.h:110
boost::asio::ip::tcp::endpoint getEndpoint() const
std::vector< boost::asio::ip::address > secureGatewayIPs_
Definition GRPCServer.h:87
std::uint16_t serverPort_
Definition GRPCServer.h:85
beast::Journal journal_
Definition GRPCServer.h:89
GRPCServer(Application &app)
Definition GRPCServer.h:302
GRPCServer & operator=(GRPCServer const &)=delete
std::thread thread_
Definition GRPCServer.h:324
boost::asio::ip::tcp::endpoint getEndpoint() const
GRPCServerImpl impl_
Definition GRPCServer.h:323
GRPCServer(GRPCServer const &)=delete
virtual void process()=0
virtual bool isFinished()=0
Processor()=default
virtual std::shared_ptr< Processor > clone()=0
Processor(Processor const &)=delete
Processor & operator=(Processor const &)=delete
virtual ~Processor()=default
A consumption charge.
Definition Charge.h:30
An endpoint that consumes resources.
Definition Consumer.h:36
T is_same_v
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
Definition algorithm.h:25
bool isUnlimited(Role const &role)
ADMIN and IDENTIFIED roles shall have unlimited resources.
Definition Role.cpp:125
Role
Indicates the level of administrative permission to grant.
Definition Role.h:44