@@ -56,7 +56,8 @@ func (e *proxyErr) Unwrap() error {
5656// component.
5757func newRpcProxy (cfg * Config , validator macaroons.MacaroonValidator ,
5858 superMacValidator session.SuperMacaroonValidator ,
59- permsMgr * perms.Manager ) * rpcProxy {
59+ permsMgr * perms.Manager , statusServer * statusServer ,
60+ subServerMgr * subServerMgr ) * rpcProxy {
6061
6162 // The gRPC web calls are protected by HTTP basic auth which is defined
6263 // by base64(username:password). Because we only have a password, we
@@ -76,6 +77,8 @@ func newRpcProxy(cfg *Config, validator macaroons.MacaroonValidator,
7677 permsMgr : permsMgr ,
7778 macValidator : validator ,
7879 superMacValidator : superMacValidator ,
80+ statusServer : statusServer ,
81+ subServerMgr : subServerMgr ,
7982 }
8083 p .grpcServer = grpc .NewServer (
8184 // From the grpxProxy doc: This codec is *crucial* to the
@@ -150,10 +153,10 @@ type rpcProxy struct {
150153
151154 superMacaroon string
152155
153- lndConn * grpc.ClientConn
154- faradayConn * grpc. ClientConn
155- loopConn * grpc. ClientConn
156- poolConn * grpc. ClientConn
156+ lndConn * grpc.ClientConn
157+
158+ statusServer * statusServer
159+ subServerMgr * subServerMgr
157160
158161 grpcServer * grpc.Server
159162 grpcWebProxy * grpcweb.WrappedGrpcServer
@@ -164,44 +167,8 @@ type rpcProxy struct {
164167
165168// Start creates initial connection to lnd.
166169func (p * rpcProxy ) Start (lndConn * grpc.ClientConn ) error {
167- var err error
168170 p .lndConn = lndConn
169171
170- // Make sure we can connect to all the daemons that are configured to be
171- // running in remote mode.
172- if p .cfg .faradayRemote {
173- p .faradayConn , err = dialBackend (
174- "faraday" , p .cfg .Remote .Faraday .RPCServer ,
175- lncfg .CleanAndExpandPath (
176- p .cfg .Remote .Faraday .TLSCertPath ,
177- ),
178- )
179- if err != nil {
180- return fmt .Errorf ("could not dial remote faraday: %v" ,
181- err )
182- }
183- }
184-
185- if p .cfg .loopRemote {
186- p .loopConn , err = dialBackend (
187- "loop" , p .cfg .Remote .Loop .RPCServer ,
188- lncfg .CleanAndExpandPath (p .cfg .Remote .Loop .TLSCertPath ),
189- )
190- if err != nil {
191- return fmt .Errorf ("could not dial remote loop: %v" , err )
192- }
193- }
194-
195- if p .cfg .poolRemote {
196- p .poolConn , err = dialBackend (
197- "pool" , p .cfg .Remote .Pool .RPCServer ,
198- lncfg .CleanAndExpandPath (p .cfg .Remote .Pool .TLSCertPath ),
199- )
200- if err != nil {
201- return fmt .Errorf ("could not dial remote pool: %v" , err )
202- }
203- }
204-
205172 // Set started to true to indicate that the rpcProxy is now ready to
206173 // handle requests.
207174 p .mu .Lock ()
@@ -215,27 +182,6 @@ func (p *rpcProxy) Start(lndConn *grpc.ClientConn) error {
215182func (p * rpcProxy ) Stop () error {
216183 p .grpcServer .Stop ()
217184
218- if p .faradayConn != nil {
219- if err := p .faradayConn .Close (); err != nil {
220- log .Errorf ("Error closing faraday connection: %v" , err )
221- return err
222- }
223- }
224-
225- if p .loopConn != nil {
226- if err := p .loopConn .Close (); err != nil {
227- log .Errorf ("Error closing loop connection: %v" , err )
228- return err
229- }
230- }
231-
232- if p .poolConn != nil {
233- if err := p .poolConn .Close (); err != nil {
234- log .Errorf ("Error closing pool connection: %v" , err )
235- return err
236- }
237- }
238-
239185 return nil
240186}
241187
@@ -306,6 +252,12 @@ func (p *rpcProxy) makeDirector(allowLitRPC bool) func(ctx context.Context,
306252
307253 outCtx := metadata .NewOutgoingContext (ctx , mdCopy )
308254
255+ // Check that the target subsystem is running.
256+ err := p .checkSubSystemStarted (requestURI )
257+ if err != nil {
258+ return nil , nil , err
259+ }
260+
309261 // Is there a basic auth or super macaroon set?
310262 authHeaders := md .Get ("authorization" )
311263 macHeader := md .Get (HeaderMacaroon )
@@ -347,26 +299,20 @@ func (p *rpcProxy) makeDirector(allowLitRPC bool) func(ctx context.Context,
347299 // since it must either be an lnd call or something that'll be
348300 // handled by the integrated daemons that are hooking into lnd's
349301 // gRPC server.
350- switch {
351- case p .permsMgr .IsFaradayURI (requestURI ) && p .cfg .faradayRemote :
352- return outCtx , p .faradayConn , nil
353-
354- case p .permsMgr .IsLoopURI (requestURI ) && p .cfg .loopRemote :
355- return outCtx , p .loopConn , nil
356-
357- case p .permsMgr .IsPoolURI (requestURI ) && p .cfg .poolRemote :
358- return outCtx , p .poolConn , nil
302+ handled , conn := p .subServerMgr .GetRemoteConn (requestURI )
303+ if handled {
304+ return outCtx , conn , nil
305+ }
359306
360307 // Calls to LiT session RPC aren't allowed in some cases.
361- case p .permsMgr .IsLitURI (requestURI ) && ! allowLitRPC :
308+ if p .permsMgr .IsLitURI (requestURI ) && ! allowLitRPC {
362309 return outCtx , nil , status .Errorf (
363310 codes .Unimplemented , "unknown service %s" ,
364311 requestURI ,
365312 )
366-
367- default :
368- return outCtx , p .lndConn , nil
369313 }
314+
315+ return outCtx , p .lndConn , nil
370316 }
371317}
372318
@@ -382,6 +328,12 @@ func (p *rpcProxy) UnaryServerInterceptor(ctx context.Context, req interface{},
382328 "required for method" , info .FullMethod )
383329 }
384330
331+ // Check that the target subsystem is running.
332+ err := p .checkSubSystemStarted (info .FullMethod )
333+ if err != nil {
334+ return nil , err
335+ }
336+
385337 // For now, basic authentication is just a quick fix until we
386338 // have proper macaroon support implemented in the UI. We allow
387339 // gRPC web requests to have it and "convert" the auth into a
@@ -423,6 +375,12 @@ func (p *rpcProxy) StreamServerInterceptor(srv interface{},
423375 "for method" , info .FullMethod )
424376 }
425377
378+ // Check that the target subsystem is running.
379+ err := p .checkSubSystemStarted (info .FullMethod )
380+ if err != nil {
381+ return err
382+ }
383+
426384 // For now, basic authentication is just a quick fix until we
427385 // have proper macaroon support implemented in the UI. We allow
428386 // gRPC web requests to have it and "convert" the auth into a
@@ -454,6 +412,35 @@ func (p *rpcProxy) StreamServerInterceptor(srv interface{},
454412 return handler (srv , ss )
455413}
456414
415+ // checkSubSystemStarted checks if the subsystem responsible for handling the
416+ // given URI has started.
417+ func (p * rpcProxy ) checkSubSystemStarted (requestURI string ) error {
418+ var system string
419+
420+ handled , subServerName := p .subServerMgr .HandledBy (requestURI )
421+
422+ switch {
423+ case handled :
424+ system = subServerName
425+
426+ case p .permsMgr .IsLndURI (requestURI ):
427+ return nil
428+
429+ case p .permsMgr .IsLitURI (requestURI ):
430+ return nil
431+
432+ default :
433+ return fmt .Errorf ("unknown gRPC web request: %v" , requestURI )
434+ }
435+
436+ started , startErr := p .statusServer .getSubServerState (system )
437+ if ! started {
438+ return fmt .Errorf ("%s is not running: %s" , system , startErr )
439+ }
440+
441+ return nil
442+ }
443+
457444// convertBasicAuth tries to convert the HTTP authorization header into a
458445// macaroon based authentication header.
459446func (p * rpcProxy ) convertBasicAuth (ctx context.Context ,
@@ -505,30 +492,15 @@ func (p *rpcProxy) basicAuthToMacaroon(basicAuth, requestURI string,
505492 macPath string
506493 macData []byte
507494 )
495+
496+ handled , path := p .subServerMgr .MacaroonPath (requestURI )
497+
508498 switch {
509499 case p .permsMgr .IsLndURI (requestURI ):
510500 _ , _ , _ , macPath , macData = p .cfg .lndConnectParams ()
511501
512- case p .permsMgr .IsFaradayURI (requestURI ):
513- if p .cfg .faradayRemote {
514- macPath = p .cfg .Remote .Faraday .MacaroonPath
515- } else {
516- macPath = p .cfg .Faraday .MacaroonPath
517- }
518-
519- case p .permsMgr .IsLoopURI (requestURI ):
520- if p .cfg .loopRemote {
521- macPath = p .cfg .Remote .Loop .MacaroonPath
522- } else {
523- macPath = p .cfg .Loop .MacaroonPath
524- }
525-
526- case p .permsMgr .IsPoolURI (requestURI ):
527- if p .cfg .poolRemote {
528- macPath = p .cfg .Remote .Pool .MacaroonPath
529- } else {
530- macPath = p .cfg .Pool .MacaroonPath
531- }
502+ case handled :
503+ macPath = path
532504
533505 case p .permsMgr .IsLitURI (requestURI ):
534506 macPath = p .cfg .MacaroonPath
@@ -607,21 +579,9 @@ func (p *rpcProxy) convertSuperMacaroon(ctx context.Context, macHex string,
607579
608580 // Is this actually a request that goes to a daemon that is running
609581 // remotely?
610- switch {
611- case p .permsMgr .IsFaradayURI (fullMethod ) && p .cfg .faradayRemote :
612- return readMacaroon (lncfg .CleanAndExpandPath (
613- p .cfg .Remote .Faraday .MacaroonPath ,
614- ))
615-
616- case p .permsMgr .IsLoopURI (fullMethod ) && p .cfg .loopRemote :
617- return readMacaroon (lncfg .CleanAndExpandPath (
618- p .cfg .Remote .Loop .MacaroonPath ,
619- ))
620-
621- case p .permsMgr .IsPoolURI (fullMethod ) && p .cfg .poolRemote :
622- return readMacaroon (lncfg .CleanAndExpandPath (
623- p .cfg .Remote .Pool .MacaroonPath ,
624- ))
582+ handled , macBytes , err := p .subServerMgr .ReadRemoteMacaroon (fullMethod )
583+ if handled {
584+ return macBytes , err
625585 }
626586
627587 return nil , nil
0 commit comments