Merge pull request #19 from guggero/server-interceptor

auth: add server interceptor
This commit is contained in:
Oliver Gugger
2020-01-07 14:37:48 +01:00
committed by GitHub
6 changed files with 106 additions and 10 deletions

32
auth/context.go Normal file
View File

@@ -0,0 +1,32 @@
package auth
import (
"context"
)
// ContextKey is the type that we use to identify LSAT specific values in the
// request context. We wrap the string inside a struct because of this comment
// in the context API: "The provided key must be comparable and should not be of
// type string or any other built-in type to avoid collisions between packages
// using context."
type ContextKey struct {
Name string
}
var (
// KeyTokenID is the key under which we store the client's token ID in
// the request context.
KeyTokenID = ContextKey{"tokenid"}
)
// FromContext tries to extract a value from the given context.
func FromContext(ctx context.Context, key ContextKey) interface{} {
return ctx.Value(key)
}
// AddToContext adds the given value to the context for easy retrieval later on.
func AddToContext(ctx context.Context, key ContextKey,
value interface{}) context.Context {
return context.WithValue(ctx, key, value)
}

View File

@@ -5,6 +5,8 @@ import (
"github.com/lightningnetwork/lnd/build"
)
const Subsystem = "AUTH"
// log is a logger that is initialized with no output filters. This
// means the package will not perform any logging by default until the caller
// requests it.
@@ -12,7 +14,7 @@ var log btclog.Logger
// The default amount of logging is none.
func init() {
UseLogger(build.NewSubLogger("AUTH", nil))
UseLogger(build.NewSubLogger(Subsystem, nil))
}
// DisableLog disables all library log output. Logging output is disabled

View File

@@ -0,0 +1,58 @@
package auth
import (
"bytes"
"context"
"net/http"
"github.com/lightninglabs/loop/lsat"
"google.golang.org/grpc"
"google.golang.org/grpc/metadata"
)
// ServerInterceptor is a gRPC server interceptor that extracts the token ID
// from the request context if an LSAT is present.
type ServerInterceptor struct{}
// UnaryInterceptor is an unary gRPC server interceptor that inspects incoming
// calls for authentication tokens. If an LSAT authentication token is found in
// the request, its token ID is extracted and treated as client ID. The
// extracted ID is then attached to the request context in a format that is easy
// to extract by request handlers.
func (i *ServerInterceptor) UnaryInterceptor(ctx context.Context,
req interface{}, _ *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (
resp interface{}, err error) {
// Try getting the authentication header embedded in the context meta
// data and parse it. We ignore all errors that happen and just forward
// the request to the handler if anything fails. Incoming calls with
// invalid metadata will therefore just be treated as non-identified or
// non-authenticated.
md, ok := metadata.FromIncomingContext(ctx)
if !ok {
return handler(ctx, req)
}
header := &http.Header{
HeaderAuthorization: md.Get(HeaderAuthorization),
}
log.Debugf("Auth header present in request: %s",
md.Get(HeaderAuthorization))
macaroon, _, err := FromHeader(header)
if err != nil {
return handler(ctx, req)
}
// If there is an LSAT, decode and add it to the context.
identifier, err := lsat.DecodeIdentifier(bytes.NewBuffer(macaroon.Id()))
if err != nil {
return handler(ctx, req)
}
var clientID lsat.TokenID
copy(clientID[:], identifier.TokenID[:])
idCtx := AddToContext(ctx, KeyTokenID, clientID)
log.Debugf("Decoded client/token ID %s from auth header",
clientID.String())
// Continue the call chain by invoking the handler.
return handler(idCtx, req)
}

4
go.mod
View File

@@ -17,8 +17,8 @@ require (
github.com/gorilla/websocket v1.4.1 // indirect
github.com/jonboulle/clockwork v0.1.0 // indirect
github.com/json-iterator/go v1.1.8 // indirect
github.com/lightninglabs/loop v0.3.0-alpha.0.20191126005026-8b8b87844035
github.com/lightningnetwork/lnd v0.8.0-beta-rc3.0.20191115230031-4d7a151b4763
github.com/lightninglabs/loop v0.3.0-alpha.0.20200103135410-5e00ce62677a
github.com/lightningnetwork/lnd v0.8.0-beta-rc3.0.20200103000305-22e1f006b194
github.com/lightningnetwork/lnd/cert v1.0.0
github.com/modern-go/reflect2 v1.0.1 // indirect
github.com/soheilhy/cmux v0.1.4 // indirect

16
go.sum
View File

@@ -79,6 +79,7 @@ github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZm
github.com/dgryski/go-sip13 v0.0.0-20181026042036-e10d5fee7954/go.mod h1:vAd38F8PWV+bWy6jNmig1y/TA+kYO4g3RSRF0IAv0no=
github.com/envoyproxy/go-control-plane v0.9.0/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4=
github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
github.com/fortytw2/leaktest v1.3.0 h1:u8491cBMTQ8ft8aeV+adlcytMZylmA5nnwwkRZjI8vw=
github.com/fortytw2/leaktest v1.3.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g=
github.com/frankban/quicktest v1.0.0/go.mod h1:R98jIehRai+d1/3Hv2//jOVCTJhW1VBavT6B6CuGq2k=
github.com/frankban/quicktest v1.2.2 h1:xfmOhhoH5fGPgbEAlhLpJH9p0z/0Qizio9osmvn9IUY=
@@ -167,18 +168,21 @@ github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE=
github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
github.com/lightninglabs/gozmq v0.0.0-20191113021534-d20a764486bf h1:HZKvJUHlcXI/f/O0Avg7t8sqkPo78HFzjmeYFl6DPnc=
github.com/lightninglabs/gozmq v0.0.0-20191113021534-d20a764486bf/go.mod h1:vxmQPeIQxPf6Jf9rM8R+B4rKBqLA2AjttNxkFBL2Plk=
github.com/lightninglabs/loop v0.3.0-alpha.0.20191126005026-8b8b87844035 h1:Sw8Ibk3xIZgneHvmAcob1uVz55DYn8mvvjbcpH9CH0w=
github.com/lightninglabs/loop v0.3.0-alpha.0.20191126005026-8b8b87844035/go.mod h1:9tvOOyUhd3AcfrxLz/dJSTHJ0ouqA+u6utJ+fBYrk9M=
github.com/lightninglabs/loop v0.3.0-alpha.0.20200103135410-5e00ce62677a h1:EiZsid2PZaanlYn5x41hKttdoxnd3rJ34SotnO4bu4Y=
github.com/lightninglabs/loop v0.3.0-alpha.0.20200103135410-5e00ce62677a/go.mod h1:VEp7TFUL7Ehq9mjQVUuNVTjpMIeTx8kOHvQ7PdJpLuA=
github.com/lightninglabs/neutrino v0.11.0 h1:lPpYFCtsfJX2W5zI4pWycPmbbBdr7zU+BafYdLoD6k0=
github.com/lightninglabs/neutrino v0.11.0/go.mod h1:CuhF0iuzg9Sp2HO6ZgXgayviFTn1QHdSTJlMncK80wg=
github.com/lightningnetwork/lightning-onion v0.0.0-20190909101754-850081b08b6a h1:GoWPN4i4jTKRxhVNh9a2vvBBO1Y2seiJB+SopUYoKyo=
github.com/lightningnetwork/lightning-onion v0.0.0-20190909101754-850081b08b6a/go.mod h1:rigfi6Af/KqsF7Za0hOgcyq2PNH4AN70AaMRxcJkff4=
github.com/lightningnetwork/lnd v0.8.0-beta-rc3.0.20191115230031-4d7a151b4763 h1:Eit9hH737th2WwnnVhkuxyMqgXce6keztGTtbDMLJ80=
github.com/lightningnetwork/lnd v0.8.0-beta-rc3.0.20191115230031-4d7a151b4763/go.mod h1:Z7DDVIgvMgyb/4+btLeiU++xt49T35PNunXGCvAaxiE=
github.com/lightninglabs/protobuf-hex-display v1.3.3-0.20191212020323-b444784ce75d/go.mod h1:KDb67YMzoh4eudnzClmvs2FbiLG9vxISmLApUkCa4uI=
github.com/lightningnetwork/lightning-onion v0.0.0-20191214001659-f34e9dc1651d h1:U50MHOOeL6gR3Ee/l0eMvZMpmRo+ydzmlQuIruCyCsA=
github.com/lightningnetwork/lightning-onion v0.0.0-20191214001659-f34e9dc1651d/go.mod h1:rigfi6Af/KqsF7Za0hOgcyq2PNH4AN70AaMRxcJkff4=
github.com/lightningnetwork/lnd v0.8.0-beta-rc3.0.20200103000305-22e1f006b194 h1:PCzjJcVWcMbkiQvzFNc3ta0JmiMprFDqzMZsSpd/km8=
github.com/lightningnetwork/lnd v0.8.0-beta-rc3.0.20200103000305-22e1f006b194/go.mod h1:WHK90FD3m2n6OyWzondS7ho0Uhtgfp30Nxvj24lQYX4=
github.com/lightningnetwork/lnd/cert v1.0.0 h1:J0gtf2UNQX2U+/j5cXnX2wIMSTuJuwrXv7m9qJr2wtw=
github.com/lightningnetwork/lnd/cert v1.0.0/go.mod h1:fmtemlSMf5t4hsQmcprSoOykypAPp+9c+0d0iqTScMo=
github.com/lightningnetwork/lnd/queue v1.0.1 h1:jzJKcTy3Nj5lQrooJ3aaw9Lau3I0IwvQR5sqtjdv2R0=
github.com/lightningnetwork/lnd/queue v1.0.1/go.mod h1:vaQwexir73flPW43Mrm7JOgJHmcEFBWWSl9HlyASoms=
github.com/lightningnetwork/lnd/queue v1.0.2 h1:Hx43fmTz2pDH4fIYDr57P/M5cB+GEMLzN+eif8576Xo=
github.com/lightningnetwork/lnd/queue v1.0.2/go.mod h1:YTkTVZCxz8tAYreH27EO3s8572ODumWrNdYW2E/YKxg=
github.com/lightningnetwork/lnd/ticker v1.0.0 h1:S1b60TEGoTtCe2A0yeB+ecoj/kkS4qpwh6l+AkQEZwU=
github.com/lightningnetwork/lnd/ticker v1.0.0/go.mod h1:iaLXJiVgI1sPANIF2qYYUJXjoksPNvGNYowB8aRbpX0=
github.com/ltcsuite/ltcd v0.0.0-20190101042124-f37f8bf35796 h1:sjOGyegMIhvgfq5oaue6Td+hxZuf3tDC8lAPrFldqFw=

2
log.go
View File

@@ -15,7 +15,7 @@ var (
func init() {
setSubLogger("MAIN", log, nil)
addSubLogger("AUTH", auth.UseLogger)
addSubLogger(auth.Subsystem, auth.UseLogger)
addSubLogger("PRXY", proxy.UseLogger)
}