feat: initial HTTP service with version and P2P endpoints

This commit is contained in:
Derrick Hammer 2024-01-10 09:19:21 -05:00
parent 3f42a66fa8
commit 584057fb8a
Signed by: pcfreak30
GPG Key ID: C997C339BE476FF2
6 changed files with 109 additions and 2 deletions

3
go.mod
View File

@ -12,12 +12,14 @@ require (
github.com/stretchr/testify v1.8.1 github.com/stretchr/testify v1.8.1
github.com/vmihailenco/msgpack/v5 v5.4.1 github.com/vmihailenco/msgpack/v5 v5.4.1
go.etcd.io/bbolt v1.3.8 go.etcd.io/bbolt v1.3.8
go.sia.tech/jape v0.11.1
go.uber.org/zap v1.26.0 go.uber.org/zap v1.26.0
nhooyr.io/websocket v1.7.1 nhooyr.io/websocket v1.7.1
) )
require ( require (
github.com/davecgh/go-spew v1.1.1 // indirect github.com/davecgh/go-spew v1.1.1 // indirect
github.com/julienschmidt/httprouter v1.3.0 // indirect
github.com/mr-tron/base58 v1.1.0 // indirect github.com/mr-tron/base58 v1.1.0 // indirect
github.com/multiformats/go-base32 v0.0.3 // indirect github.com/multiformats/go-base32 v0.0.3 // indirect
github.com/multiformats/go-base36 v0.1.0 // indirect github.com/multiformats/go-base36 v0.1.0 // indirect
@ -26,5 +28,6 @@ require (
go.uber.org/multierr v1.11.0 // indirect go.uber.org/multierr v1.11.0 // indirect
golang.org/x/net v0.17.0 // indirect golang.org/x/net v0.17.0 // indirect
golang.org/x/sys v0.15.0 // indirect golang.org/x/sys v0.15.0 // indirect
golang.org/x/tools v0.6.0 // indirect
gopkg.in/yaml.v3 v3.0.1 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect
) )

12
interfaces/http.go Normal file
View File

@ -0,0 +1,12 @@
package interfaces
import (
"github.com/julienschmidt/httprouter"
)
//go:generate mockgen -source=http.go -destination=../mocks/interfaces/http.go -package=interfaces
type HTTPService interface {
Service
GetHandler() *httprouter.Router
}

View File

@ -11,5 +11,6 @@ type Service interface {
type Services interface { type Services interface {
P2P() P2PService P2P() P2PService
Registry() RegistryService Registry() RegistryService
HTTP() HTTPService
All() []Service All() []Service
} }

View File

@ -15,6 +15,7 @@ import (
"git.lumeweb.com/LumeWeb/libs5-go/types" "git.lumeweb.com/LumeWeb/libs5-go/types"
"git.lumeweb.com/LumeWeb/libs5-go/utils" "git.lumeweb.com/LumeWeb/libs5-go/utils"
"github.com/go-resty/resty/v2" "github.com/go-resty/resty/v2"
"github.com/julienschmidt/httprouter"
"github.com/vmihailenco/msgpack/v5" "github.com/vmihailenco/msgpack/v5"
bolt "go.etcd.io/bbolt" bolt "go.etcd.io/bbolt"
"go.uber.org/zap" "go.uber.org/zap"
@ -52,7 +53,7 @@ func NewNode(config *config.NodeConfig) interfaces.Node {
hashQueryRoutingTable: structs.NewMap(), hashQueryRoutingTable: structs.NewMap(),
httpClient: resty.New(), httpClient: resty.New(),
} }
n.services = NewServices(service.NewP2P(n), service.NewRegistry(n)) n.services = NewServices(service.NewP2P(n), service.NewRegistry(n), service.NewHTTP(n))
return n return n
} }
@ -333,3 +334,7 @@ func (n *NodeImpl) WaitOnConnectedPeers() {
func (n *NodeImpl) ConnectionTracker() *sync.WaitGroup { func (n *NodeImpl) ConnectionTracker() *sync.WaitGroup {
return &n.connections return &n.connections
} }
func (n *NodeImpl) HTTPRouter() *httprouter.Router {
return n.services.HTTP().GetHandler()
}

View File

@ -9,12 +9,18 @@ var (
type ServicesImpl struct { type ServicesImpl struct {
p2p interfaces.P2PService p2p interfaces.P2PService
registry interfaces.RegistryService registry interfaces.RegistryService
http interfaces.HTTPService
}
func (s *ServicesImpl) HTTP() interfaces.HTTPService {
return s.http
} }
func (s *ServicesImpl) All() []interfaces.Service { func (s *ServicesImpl) All() []interfaces.Service {
services := make([]interfaces.Service, 0) services := make([]interfaces.Service, 0)
services = append(services, s.p2p) services = append(services, s.p2p)
services = append(services, s.registry) services = append(services, s.registry)
services = append(services, s.http)
return services return services
} }
@ -23,10 +29,11 @@ func (s *ServicesImpl) Registry() interfaces.RegistryService {
return s.registry return s.registry
} }
func NewServices(p2p interfaces.P2PService, registry interfaces.RegistryService) interfaces.Services { func NewServices(p2p interfaces.P2PService, registry interfaces.RegistryService, http interfaces.HTTPService) interfaces.Services {
return &ServicesImpl{ return &ServicesImpl{
p2p: p2p, p2p: p2p,
registry: registry, registry: registry,
http: http,
} }
} }

79
service/http.go Normal file
View File

@ -0,0 +1,79 @@
package service
import (
"git.lumeweb.com/LumeWeb/libs5-go/build"
"git.lumeweb.com/LumeWeb/libs5-go/interfaces"
"git.lumeweb.com/LumeWeb/libs5-go/net"
"github.com/julienschmidt/httprouter"
"go.sia.tech/jape"
"go.uber.org/zap"
"net/url"
"nhooyr.io/websocket"
)
var _ interfaces.HTTPService = (*HTTPImpl)(nil)
type HTTPImpl struct {
node interfaces.Node
}
func NewHTTP(node interfaces.Node) *HTTPImpl {
return &HTTPImpl{node: node}
}
func (h *HTTPImpl) GetHandler() *httprouter.Router {
mux := jape.Mux(map[string]jape.Handler{
"GET /s5/version": h.versionHandler,
"GET /s5/p2p": h.p2pHandler,
})
return mux
}
func (h *HTTPImpl) Node() interfaces.Node {
return h.node
}
func (h *HTTPImpl) Start() error {
return nil
}
func (h *HTTPImpl) Stop() error {
return nil
}
func (h *HTTPImpl) Init() error {
return nil
}
func (h *HTTPImpl) versionHandler(ctx jape.Context) {
_, _ = ctx.ResponseWriter.Write([]byte(build.Version))
}
func (h *HTTPImpl) p2pHandler(ctx jape.Context) {
c, err := websocket.Accept(ctx.ResponseWriter, ctx.Request, nil)
if err != nil {
h.node.Logger().Error("error accepting websocket connection", zap.Error(err))
return
}
peer, err := net.CreateTransportPeer("wss", &net.TransportPeerConfig{
Socket: c,
Uris: []*url.URL{},
})
if err != nil {
h.node.Logger().Error("error creating transport peer", zap.Error(err))
err := c.Close(websocket.StatusInternalError, "the sky is falling")
if err != nil {
h.node.Logger().Error("error closing websocket connection", zap.Error(err))
}
return
}
go func() {
err := h.node.Services().P2P().OnNewPeer(peer, true)
if err != nil {
h.node.Logger().Error("error handling new peer", zap.Error(err))
}
h.node.ConnectionTracker().Done()
}()
}