mirror of
https://github.com/h44z/wg-portal.git
synced 2025-04-17 07:55:13 +00:00
chore: use interfaces for web related services
This commit is contained in:
parent
678b6c6456
commit
02ed7b19df
@ -109,10 +109,10 @@ func main() {
|
||||
apiV0Session := handlersV0.NewSessionWrapper(cfg)
|
||||
apiV0Auth := handlersV0.NewAuthenticationHandler(authenticator, apiV0Session)
|
||||
|
||||
apiV0EndpointAuth := handlersV0.NewAuthEndpoint(backend, apiV0Auth, apiV0Session, validatorManager)
|
||||
apiV0EndpointUsers := handlersV0.NewUserEndpoint(backend, apiV0Auth, validatorManager)
|
||||
apiV0EndpointInterfaces := handlersV0.NewInterfaceEndpoint(backend, apiV0Auth, validatorManager)
|
||||
apiV0EndpointPeers := handlersV0.NewPeerEndpoint(backend, apiV0Auth, validatorManager)
|
||||
apiV0EndpointAuth := handlersV0.NewAuthEndpoint(cfg, apiV0Auth, apiV0Session, validatorManager, backend)
|
||||
apiV0EndpointUsers := handlersV0.NewUserEndpoint(cfg, apiV0Auth, validatorManager, backend)
|
||||
apiV0EndpointInterfaces := handlersV0.NewInterfaceEndpoint(cfg, apiV0Auth, validatorManager, backend)
|
||||
apiV0EndpointPeers := handlersV0.NewPeerEndpoint(cfg, apiV0Auth, validatorManager, backend)
|
||||
apiV0EndpointConfig := handlersV0.NewConfigEndpoint(cfg, apiV0Auth)
|
||||
apiV0EndpointTest := handlersV0.NewTestEndpoint(apiV0Auth)
|
||||
|
||||
|
@ -36,13 +36,6 @@ type Handler interface {
|
||||
RegisterRoutes(g *routegroup.Bundle)
|
||||
}
|
||||
|
||||
type Authenticator interface {
|
||||
// LoggedIn checks if a user is logged in. If scopes are given, they are validated as well.
|
||||
LoggedIn(scopes ...Scope) func(next http.Handler) http.Handler
|
||||
// UserIdMatch checks if the user id in the session matches the user id in the request. If not, the request is aborted.
|
||||
UserIdMatch(idParameter string) func(next http.Handler) http.Handler
|
||||
}
|
||||
|
||||
// To compile the API documentation use the
|
||||
// api_build_tool
|
||||
// command that can be found in the $PROJECT_ROOT/cmd/api_build_tool directory.
|
||||
@ -97,6 +90,27 @@ func handleCsrfGet() http.HandlerFunc {
|
||||
}
|
||||
}
|
||||
|
||||
// region session wrapper
|
||||
// region handler-interfaces
|
||||
|
||||
// endregion session wrapper
|
||||
type Authenticator interface {
|
||||
// LoggedIn checks if a user is logged in. If scopes are given, they are validated as well.
|
||||
LoggedIn(scopes ...Scope) func(next http.Handler) http.Handler
|
||||
// UserIdMatch checks if the user id in the session matches the user id in the request. If not, the request is aborted.
|
||||
UserIdMatch(idParameter string) func(next http.Handler) http.Handler
|
||||
}
|
||||
|
||||
type Session interface {
|
||||
// SetData sets the session data for the given context.
|
||||
SetData(ctx context.Context, val SessionData)
|
||||
// GetData returns the session data for the given context. If no data is found, the default session data is returned.
|
||||
GetData(ctx context.Context) SessionData
|
||||
// DestroyData destroys the session data for the given context.
|
||||
DestroyData(ctx context.Context)
|
||||
}
|
||||
|
||||
type Validator interface {
|
||||
// Struct validates the given struct.
|
||||
Struct(s interface{}) error
|
||||
}
|
||||
|
||||
// endregion handler-interfaces
|
||||
|
@ -5,6 +5,9 @@ import (
|
||||
"strings"
|
||||
)
|
||||
|
||||
// Base64UrlDecode decodes a base64 url encoded string.
|
||||
// In comparison to the standard base64 encoding, the url encoding uses - instead of + and _ instead of /
|
||||
// as well as . instead of =.
|
||||
func Base64UrlDecode(in string) string {
|
||||
in = strings.ReplaceAll(in, "-", "=")
|
||||
in = strings.ReplaceAll(in, "_", "/")
|
||||
|
@ -10,36 +10,42 @@ import (
|
||||
|
||||
"github.com/go-pkgz/routegroup"
|
||||
|
||||
"github.com/h44z/wg-portal/internal/app"
|
||||
"github.com/h44z/wg-portal/internal/app/api/core/request"
|
||||
"github.com/h44z/wg-portal/internal/app/api/core/respond"
|
||||
"github.com/h44z/wg-portal/internal/app/api/v0/model"
|
||||
"github.com/h44z/wg-portal/internal/config"
|
||||
"github.com/h44z/wg-portal/internal/domain"
|
||||
)
|
||||
|
||||
type Session interface {
|
||||
// SetData sets the session data for the given context.
|
||||
SetData(ctx context.Context, val SessionData)
|
||||
// GetData returns the session data for the given context. If no data is found, the default session data is returned.
|
||||
GetData(ctx context.Context) SessionData
|
||||
// DestroyData destroys the session data for the given context.
|
||||
DestroyData(ctx context.Context)
|
||||
}
|
||||
|
||||
type Validator interface {
|
||||
Struct(s interface{}) error
|
||||
type AuthenticationService interface {
|
||||
// GetExternalLoginProviders returns a list of all available external login providers.
|
||||
GetExternalLoginProviders(_ context.Context) []domain.LoginProviderInfo
|
||||
// PlainLogin authenticates a user with a username and password.
|
||||
PlainLogin(ctx context.Context, username, password string) (*domain.User, error)
|
||||
// OauthLoginStep1 initiates the OAuth login flow.
|
||||
OauthLoginStep1(_ context.Context, providerId string) (authCodeUrl, state, nonce string, err error)
|
||||
// OauthLoginStep2 completes the OAuth login flow and logins the user in.
|
||||
OauthLoginStep2(ctx context.Context, providerId, nonce, code string) (*domain.User, error)
|
||||
}
|
||||
|
||||
type AuthEndpoint struct {
|
||||
app *app.App
|
||||
cfg *config.Config
|
||||
authService AuthenticationService
|
||||
authenticator Authenticator
|
||||
session Session
|
||||
validate Validator
|
||||
}
|
||||
|
||||
func NewAuthEndpoint(app *app.App, authenticator Authenticator, session Session, validator Validator) AuthEndpoint {
|
||||
func NewAuthEndpoint(
|
||||
cfg *config.Config,
|
||||
authenticator Authenticator,
|
||||
session Session,
|
||||
validator Validator,
|
||||
authService AuthenticationService,
|
||||
) AuthEndpoint {
|
||||
return AuthEndpoint{
|
||||
app: app,
|
||||
cfg: cfg,
|
||||
authService: authService,
|
||||
authenticator: authenticator,
|
||||
session: session,
|
||||
validate: validator,
|
||||
@ -73,7 +79,7 @@ func (e AuthEndpoint) RegisterRoutes(g *routegroup.Bundle) {
|
||||
// @Router /auth/providers [get]
|
||||
func (e AuthEndpoint) handleExternalLoginProvidersGet() http.HandlerFunc {
|
||||
return func(w http.ResponseWriter, r *http.Request) {
|
||||
providers := e.app.Authenticator.GetExternalLoginProviders(r.Context())
|
||||
providers := e.authService.GetExternalLoginProviders(r.Context())
|
||||
|
||||
respond.JSON(w, http.StatusOK, model.NewLoginProviderInfos(providers))
|
||||
}
|
||||
@ -169,7 +175,7 @@ func (e AuthEndpoint) handleOauthInitiateGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
authCodeUrl, state, nonce, err := e.app.Authenticator.OauthLoginStep1(context.Background(), provider)
|
||||
authCodeUrl, state, nonce, err := e.authService.OauthLoginStep1(context.Background(), provider)
|
||||
if err != nil {
|
||||
if autoRedirect && e.isValidReturnUrl(returnTo) {
|
||||
redirectToReturn()
|
||||
@ -262,7 +268,8 @@ func (e AuthEndpoint) handleOauthCallbackGet() http.HandlerFunc {
|
||||
}
|
||||
|
||||
loginCtx, cancel := context.WithTimeout(context.Background(), 1000*time.Second)
|
||||
user, err := e.app.Authenticator.OauthLoginStep2(loginCtx, provider, currentSession.OauthNonce, oauthCode)
|
||||
user, err := e.authService.OauthLoginStep2(loginCtx, provider, currentSession.OauthNonce,
|
||||
oauthCode)
|
||||
cancel()
|
||||
if err != nil {
|
||||
if returnUrl != nil && e.isValidReturnUrl(returnUrl.String()) {
|
||||
@ -335,7 +342,8 @@ func (e AuthEndpoint) handleLoginPost() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
user, err := e.app.Authenticator.PlainLogin(context.Background(), loginData.Username, loginData.Password)
|
||||
user, err := e.authService.PlainLogin(context.Background(), loginData.Username,
|
||||
loginData.Password)
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusUnauthorized,
|
||||
model.Error{Code: http.StatusUnauthorized, Message: "login failed"})
|
||||
@ -372,7 +380,7 @@ func (e AuthEndpoint) handleLogoutPost() http.HandlerFunc {
|
||||
|
||||
// isValidReturnUrl checks if the given return URL matches the configured external URL of the application.
|
||||
func (e AuthEndpoint) isValidReturnUrl(returnUrl string) bool {
|
||||
if !strings.HasPrefix(returnUrl, e.app.Config.Web.ExternalUrl) {
|
||||
if !strings.HasPrefix(returnUrl, e.cfg.Web.ExternalUrl) {
|
||||
return false
|
||||
}
|
||||
|
||||
|
@ -1,29 +1,58 @@
|
||||
package handlers
|
||||
|
||||
import (
|
||||
"context"
|
||||
"io"
|
||||
"net/http"
|
||||
|
||||
"github.com/go-pkgz/routegroup"
|
||||
|
||||
"github.com/h44z/wg-portal/internal/app"
|
||||
"github.com/h44z/wg-portal/internal/app/api/core/request"
|
||||
"github.com/h44z/wg-portal/internal/app/api/core/respond"
|
||||
"github.com/h44z/wg-portal/internal/app/api/v0/model"
|
||||
"github.com/h44z/wg-portal/internal/config"
|
||||
"github.com/h44z/wg-portal/internal/domain"
|
||||
)
|
||||
|
||||
type InterfaceEndpoint struct {
|
||||
app *app.App
|
||||
authenticator Authenticator
|
||||
validator Validator
|
||||
type InterfaceService interface {
|
||||
// GetInterfaceAndPeers returns the interface with the given id and all peers associated with it.
|
||||
GetInterfaceAndPeers(ctx context.Context, id domain.InterfaceIdentifier) (*domain.Interface, []domain.Peer, error)
|
||||
// PrepareInterface returns a new interface with default values.
|
||||
PrepareInterface(ctx context.Context) (*domain.Interface, error)
|
||||
// CreateInterface creates a new interface.
|
||||
CreateInterface(ctx context.Context, in *domain.Interface) (*domain.Interface, error)
|
||||
// UpdateInterface updates the interface with the given id.
|
||||
UpdateInterface(ctx context.Context, in *domain.Interface) (*domain.Interface, []domain.Peer, error)
|
||||
// DeleteInterface deletes the interface with the given id.
|
||||
DeleteInterface(ctx context.Context, id domain.InterfaceIdentifier) error
|
||||
// GetAllInterfacesAndPeers returns all interfaces and all peers associated with them.
|
||||
GetAllInterfacesAndPeers(ctx context.Context) ([]domain.Interface, [][]domain.Peer, error)
|
||||
// GetInterfaceConfig returns the interface configuration as string.
|
||||
GetInterfaceConfig(ctx context.Context, id domain.InterfaceIdentifier) (io.Reader, error)
|
||||
// PersistInterfaceConfig persists the interface configuration to a file.
|
||||
PersistInterfaceConfig(ctx context.Context, id domain.InterfaceIdentifier) error
|
||||
// ApplyPeerDefaults applies the peer defaults to all peers of the given interface.
|
||||
ApplyPeerDefaults(ctx context.Context, in *domain.Interface) error
|
||||
}
|
||||
|
||||
func NewInterfaceEndpoint(app *app.App, authenticator Authenticator, validator Validator) InterfaceEndpoint {
|
||||
type InterfaceEndpoint struct {
|
||||
cfg *config.Config
|
||||
interfaceService InterfaceService
|
||||
authenticator Authenticator
|
||||
validator Validator
|
||||
}
|
||||
|
||||
func NewInterfaceEndpoint(
|
||||
cfg *config.Config,
|
||||
authenticator Authenticator,
|
||||
validator Validator,
|
||||
interfaceService InterfaceService,
|
||||
) InterfaceEndpoint {
|
||||
return InterfaceEndpoint{
|
||||
app: app,
|
||||
authenticator: authenticator,
|
||||
validator: validator,
|
||||
cfg: cfg,
|
||||
interfaceService: interfaceService,
|
||||
authenticator: authenticator,
|
||||
validator: validator,
|
||||
}
|
||||
}
|
||||
|
||||
@ -59,7 +88,7 @@ func (e InterfaceEndpoint) RegisterRoutes(g *routegroup.Bundle) {
|
||||
// @Router /interface/prepare [get]
|
||||
func (e InterfaceEndpoint) handlePrepareGet() http.HandlerFunc {
|
||||
return func(w http.ResponseWriter, r *http.Request) {
|
||||
in, err := e.app.PrepareInterface(r.Context())
|
||||
in, err := e.interfaceService.PrepareInterface(r.Context())
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -82,7 +111,7 @@ func (e InterfaceEndpoint) handlePrepareGet() http.HandlerFunc {
|
||||
// @Router /interface/all [get]
|
||||
func (e InterfaceEndpoint) handleAllGet() http.HandlerFunc {
|
||||
return func(w http.ResponseWriter, r *http.Request) {
|
||||
interfaces, peers, err := e.app.GetAllInterfacesAndPeers(r.Context())
|
||||
interfaces, peers, err := e.interfaceService.GetAllInterfacesAndPeers(r.Context())
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -114,7 +143,7 @@ func (e InterfaceEndpoint) handleSingleGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
iface, peers, err := e.app.GetInterfaceAndPeers(r.Context(), domain.InterfaceIdentifier(id))
|
||||
iface, peers, err := e.interfaceService.GetInterfaceAndPeers(r.Context(), domain.InterfaceIdentifier(id))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -146,7 +175,7 @@ func (e InterfaceEndpoint) handleConfigGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
config, err := e.app.GetInterfaceConfig(r.Context(), domain.InterfaceIdentifier(id))
|
||||
config, err := e.interfaceService.GetInterfaceConfig(r.Context(), domain.InterfaceIdentifier(id))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -203,7 +232,7 @@ func (e InterfaceEndpoint) handleUpdatePut() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
updatedInterface, peers, err := e.app.UpdateInterface(r.Context(), model.NewDomainInterface(&in))
|
||||
updatedInterface, peers, err := e.interfaceService.UpdateInterface(r.Context(), model.NewDomainInterface(&in))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -238,7 +267,7 @@ func (e InterfaceEndpoint) handleCreatePost() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
newInterface, err := e.app.CreateInterface(r.Context(), model.NewDomainInterface(&in))
|
||||
newInterface, err := e.interfaceService.CreateInterface(r.Context(), model.NewDomainInterface(&in))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -269,7 +298,7 @@ func (e InterfaceEndpoint) handlePeersGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
_, peers, err := e.app.GetInterfaceAndPeers(r.Context(), domain.InterfaceIdentifier(id))
|
||||
_, peers, err := e.interfaceService.GetInterfaceAndPeers(r.Context(), domain.InterfaceIdentifier(id))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -301,7 +330,7 @@ func (e InterfaceEndpoint) handleDelete() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
err := e.app.DeleteInterface(r.Context(), domain.InterfaceIdentifier(id))
|
||||
err := e.interfaceService.DeleteInterface(r.Context(), domain.InterfaceIdentifier(id))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -333,7 +362,7 @@ func (e InterfaceEndpoint) handleSaveConfigPost() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
err := e.app.PersistInterfaceConfig(r.Context(), domain.InterfaceIdentifier(id))
|
||||
err := e.interfaceService.PersistInterfaceConfig(r.Context(), domain.InterfaceIdentifier(id))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -382,7 +411,7 @@ func (e InterfaceEndpoint) handleApplyPeerDefaultsPost() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
if err := e.app.ApplyPeerDefaults(r.Context(), model.NewDomainInterface(&in)); err != nil {
|
||||
if err := e.interfaceService.ApplyPeerDefaults(r.Context(), model.NewDomainInterface(&in)); err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
})
|
||||
|
@ -1,27 +1,64 @@
|
||||
package handlers
|
||||
|
||||
import (
|
||||
"context"
|
||||
"io"
|
||||
"net/http"
|
||||
|
||||
"github.com/go-pkgz/routegroup"
|
||||
|
||||
"github.com/h44z/wg-portal/internal/app"
|
||||
"github.com/h44z/wg-portal/internal/app/api/core/request"
|
||||
"github.com/h44z/wg-portal/internal/app/api/core/respond"
|
||||
"github.com/h44z/wg-portal/internal/app/api/v0/model"
|
||||
"github.com/h44z/wg-portal/internal/config"
|
||||
"github.com/h44z/wg-portal/internal/domain"
|
||||
)
|
||||
|
||||
type PeerService interface {
|
||||
// GetInterfaceAndPeers returns the interface with the given id and all peers associated with it.
|
||||
GetInterfaceAndPeers(ctx context.Context, id domain.InterfaceIdentifier) (*domain.Interface, []domain.Peer, error)
|
||||
// PreparePeer returns a new peer with default values for the given interface.
|
||||
PreparePeer(ctx context.Context, id domain.InterfaceIdentifier) (*domain.Peer, error)
|
||||
// GetPeer returns the peer with the given id.
|
||||
GetPeer(ctx context.Context, id domain.PeerIdentifier) (*domain.Peer, error)
|
||||
// CreatePeer creates a new peer.
|
||||
CreatePeer(ctx context.Context, peer *domain.Peer) (*domain.Peer, error)
|
||||
// CreateMultiplePeers creates multiple new peers.
|
||||
CreateMultiplePeers(
|
||||
ctx context.Context,
|
||||
interfaceId domain.InterfaceIdentifier,
|
||||
r *domain.PeerCreationRequest,
|
||||
) ([]domain.Peer, error)
|
||||
// UpdatePeer updates the peer with the given id.
|
||||
UpdatePeer(ctx context.Context, peer *domain.Peer) (*domain.Peer, error)
|
||||
// DeletePeer deletes the peer with the given id.
|
||||
DeletePeer(ctx context.Context, id domain.PeerIdentifier) error
|
||||
// GetPeerConfig returns the peer configuration for the given id.
|
||||
GetPeerConfig(ctx context.Context, id domain.PeerIdentifier) (io.Reader, error)
|
||||
// GetPeerConfigQrCode returns the peer configuration as qr code for the given id.
|
||||
GetPeerConfigQrCode(ctx context.Context, id domain.PeerIdentifier) (io.Reader, error)
|
||||
// SendPeerEmail sends the peer configuration via email.
|
||||
SendPeerEmail(ctx context.Context, linkOnly bool, peers ...domain.PeerIdentifier) error
|
||||
// GetPeerStats returns the peer stats for the given interface.
|
||||
GetPeerStats(ctx context.Context, id domain.InterfaceIdentifier) ([]domain.PeerStatus, error)
|
||||
}
|
||||
|
||||
type PeerEndpoint struct {
|
||||
app *app.App
|
||||
cfg *config.Config
|
||||
peerService PeerService
|
||||
authenticator Authenticator
|
||||
validator Validator
|
||||
}
|
||||
|
||||
func NewPeerEndpoint(app *app.App, authenticator Authenticator, validator Validator) PeerEndpoint {
|
||||
func NewPeerEndpoint(
|
||||
cfg *config.Config,
|
||||
authenticator Authenticator,
|
||||
validator Validator,
|
||||
peerService PeerService,
|
||||
) PeerEndpoint {
|
||||
return PeerEndpoint{
|
||||
app: app,
|
||||
cfg: cfg,
|
||||
peerService: peerService,
|
||||
authenticator: authenticator,
|
||||
validator: validator,
|
||||
}
|
||||
@ -69,7 +106,7 @@ func (e PeerEndpoint) handleAllGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
_, peers, err := e.app.GetInterfaceAndPeers(r.Context(), domain.InterfaceIdentifier(interfaceId))
|
||||
_, peers, err := e.peerService.GetInterfaceAndPeers(r.Context(), domain.InterfaceIdentifier(interfaceId))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -100,7 +137,7 @@ func (e PeerEndpoint) handleSingleGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
peer, err := e.app.GetPeer(r.Context(), domain.PeerIdentifier(peerId))
|
||||
peer, err := e.peerService.GetPeer(r.Context(), domain.PeerIdentifier(peerId))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -131,7 +168,7 @@ func (e PeerEndpoint) handlePrepareGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
peer, err := e.app.PreparePeer(r.Context(), domain.InterfaceIdentifier(interfaceId))
|
||||
peer, err := e.peerService.PreparePeer(r.Context(), domain.InterfaceIdentifier(interfaceId))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -179,7 +216,7 @@ func (e PeerEndpoint) handleCreatePost() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
newPeer, err := e.app.CreatePeer(r.Context(), model.NewDomainPeer(&p))
|
||||
newPeer, err := e.peerService.CreatePeer(r.Context(), model.NewDomainPeer(&p))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -221,7 +258,7 @@ func (e PeerEndpoint) handleCreateMultiplePost() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
newPeers, err := e.app.CreateMultiplePeers(r.Context(), domain.InterfaceIdentifier(interfaceId),
|
||||
newPeers, err := e.peerService.CreateMultiplePeers(r.Context(), domain.InterfaceIdentifier(interfaceId),
|
||||
model.NewDomainPeerCreationRequest(&req))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
@ -270,7 +307,7 @@ func (e PeerEndpoint) handleUpdatePut() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
updatedPeer, err := e.app.UpdatePeer(r.Context(), model.NewDomainPeer(&p))
|
||||
updatedPeer, err := e.peerService.UpdatePeer(r.Context(), model.NewDomainPeer(&p))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -300,7 +337,7 @@ func (e PeerEndpoint) handleDelete() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
err := e.app.DeletePeer(r.Context(), domain.PeerIdentifier(id))
|
||||
err := e.peerService.DeletePeer(r.Context(), domain.PeerIdentifier(id))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -332,7 +369,7 @@ func (e PeerEndpoint) handleConfigGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
config, err := e.app.GetPeerConfig(r.Context(), domain.PeerIdentifier(id))
|
||||
configTxt, err := e.peerService.GetPeerConfig(r.Context(), domain.PeerIdentifier(id))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -340,7 +377,7 @@ func (e PeerEndpoint) handleConfigGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
configString, err := io.ReadAll(config)
|
||||
configTxtString, err := io.ReadAll(configTxt)
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -348,7 +385,7 @@ func (e PeerEndpoint) handleConfigGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
respond.JSON(w, http.StatusOK, string(configString))
|
||||
respond.JSON(w, http.StatusOK, string(configTxtString))
|
||||
}
|
||||
}
|
||||
|
||||
@ -374,7 +411,7 @@ func (e PeerEndpoint) handleQrCodeGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
config, err := e.app.GetPeerConfigQrCode(r.Context(), domain.PeerIdentifier(id))
|
||||
configQr, err := e.peerService.GetPeerConfigQrCode(r.Context(), domain.PeerIdentifier(id))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -382,7 +419,7 @@ func (e PeerEndpoint) handleQrCodeGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
configData, err := io.ReadAll(config)
|
||||
configQrData, err := io.ReadAll(configQr)
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError, model.Error{
|
||||
Code: http.StatusInternalServerError, Message: err.Error(),
|
||||
@ -390,7 +427,7 @@ func (e PeerEndpoint) handleQrCodeGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
respond.Data(w, http.StatusOK, "image/png", configData)
|
||||
respond.Data(w, http.StatusOK, "image/png", configQrData)
|
||||
}
|
||||
}
|
||||
|
||||
@ -427,7 +464,7 @@ func (e PeerEndpoint) handleEmailPost() http.HandlerFunc {
|
||||
for i := range req.Identifiers {
|
||||
peerIds[i] = domain.PeerIdentifier(req.Identifiers[i])
|
||||
}
|
||||
if err := e.app.SendPeerEmail(r.Context(), req.LinkOnly, peerIds...); err != nil {
|
||||
if err := e.peerService.SendPeerEmail(r.Context(), req.LinkOnly, peerIds...); err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
return
|
||||
@ -457,13 +494,13 @@ func (e PeerEndpoint) handleStatsGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
stats, err := e.app.GetPeerStats(r.Context(), domain.InterfaceIdentifier(interfaceId))
|
||||
stats, err := e.peerService.GetPeerStats(r.Context(), domain.InterfaceIdentifier(interfaceId))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
return
|
||||
}
|
||||
|
||||
respond.JSON(w, http.StatusOK, model.NewPeerStats(e.app.Config.Statistics.CollectPeerData, stats))
|
||||
respond.JSON(w, http.StatusOK, model.NewPeerStats(e.cfg.Statistics.CollectPeerData, stats))
|
||||
}
|
||||
}
|
||||
|
@ -1,26 +1,57 @@
|
||||
package handlers
|
||||
|
||||
import (
|
||||
"context"
|
||||
"net/http"
|
||||
|
||||
"github.com/go-pkgz/routegroup"
|
||||
|
||||
"github.com/h44z/wg-portal/internal/app"
|
||||
"github.com/h44z/wg-portal/internal/app/api/core/request"
|
||||
"github.com/h44z/wg-portal/internal/app/api/core/respond"
|
||||
"github.com/h44z/wg-portal/internal/app/api/v0/model"
|
||||
"github.com/h44z/wg-portal/internal/config"
|
||||
"github.com/h44z/wg-portal/internal/domain"
|
||||
)
|
||||
|
||||
type UserService interface {
|
||||
// GetUser returns the user with the given id.
|
||||
GetUser(ctx context.Context, id domain.UserIdentifier) (*domain.User, error)
|
||||
// GetAllUsers returns all users.
|
||||
GetAllUsers(ctx context.Context) ([]domain.User, error)
|
||||
// UpdateUser updates the user with the given id.
|
||||
UpdateUser(ctx context.Context, user *domain.User) (*domain.User, error)
|
||||
// CreateUser creates a new user.
|
||||
CreateUser(ctx context.Context, user *domain.User) (*domain.User, error)
|
||||
// DeleteUser deletes the user with the given id.
|
||||
DeleteUser(ctx context.Context, id domain.UserIdentifier) error
|
||||
// ActivateApi enables the API for the user with the given id.
|
||||
ActivateApi(ctx context.Context, id domain.UserIdentifier) (*domain.User, error)
|
||||
// DeactivateApi disables the API for the user with the given id.
|
||||
DeactivateApi(ctx context.Context, id domain.UserIdentifier) (*domain.User, error)
|
||||
// GetUserPeers returns all peers for the given user.
|
||||
GetUserPeers(ctx context.Context, id domain.UserIdentifier) ([]domain.Peer, error)
|
||||
// GetUserPeerStats returns all peer stats for the given user.
|
||||
GetUserPeerStats(ctx context.Context, id domain.UserIdentifier) ([]domain.PeerStatus, error)
|
||||
// GetUserInterfaces returns all interfaces for the given user.
|
||||
GetUserInterfaces(ctx context.Context, id domain.UserIdentifier) ([]domain.Interface, error)
|
||||
}
|
||||
|
||||
type UserEndpoint struct {
|
||||
app *app.App
|
||||
cfg *config.Config
|
||||
userService UserService
|
||||
authenticator Authenticator
|
||||
validator Validator
|
||||
}
|
||||
|
||||
func NewUserEndpoint(app *app.App, authenticator Authenticator, validator Validator) UserEndpoint {
|
||||
func NewUserEndpoint(
|
||||
cfg *config.Config,
|
||||
authenticator Authenticator,
|
||||
validator Validator,
|
||||
userService UserService,
|
||||
) UserEndpoint {
|
||||
return UserEndpoint{
|
||||
app: app,
|
||||
cfg: cfg,
|
||||
userService: userService,
|
||||
authenticator: authenticator,
|
||||
validator: validator,
|
||||
}
|
||||
@ -57,7 +88,7 @@ func (e UserEndpoint) RegisterRoutes(g *routegroup.Bundle) {
|
||||
// @Router /user/all [get]
|
||||
func (e UserEndpoint) handleAllGet() http.HandlerFunc {
|
||||
return func(w http.ResponseWriter, r *http.Request) {
|
||||
users, err := e.app.GetAllUsers(r.Context())
|
||||
users, err := e.userService.GetAllUsers(r.Context())
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -86,7 +117,7 @@ func (e UserEndpoint) handleSingleGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
user, err := e.app.GetUser(r.Context(), domain.UserIdentifier(id))
|
||||
user, err := e.userService.GetUser(r.Context(), domain.UserIdentifier(id))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -133,7 +164,7 @@ func (e UserEndpoint) handleUpdatePut() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
updateUser, err := e.app.UpdateUser(r.Context(), model.NewDomainUser(&user))
|
||||
updateUser, err := e.userService.UpdateUser(r.Context(), model.NewDomainUser(&user))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -167,7 +198,7 @@ func (e UserEndpoint) handleCreatePost() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
newUser, err := e.app.CreateUser(r.Context(), model.NewDomainUser(&user))
|
||||
newUser, err := e.userService.CreateUser(r.Context(), model.NewDomainUser(&user))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -198,7 +229,7 @@ func (e UserEndpoint) handlePeersGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
peers, err := e.app.GetUserPeers(r.Context(), domain.UserIdentifier(userId))
|
||||
peers, err := e.userService.GetUserPeers(r.Context(), domain.UserIdentifier(userId))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -229,14 +260,14 @@ func (e UserEndpoint) handleStatsGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
stats, err := e.app.GetUserPeerStats(r.Context(), domain.UserIdentifier(userId))
|
||||
stats, err := e.userService.GetUserPeerStats(r.Context(), domain.UserIdentifier(userId))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
return
|
||||
}
|
||||
|
||||
respond.JSON(w, http.StatusOK, model.NewPeerStats(e.app.Config.Statistics.CollectPeerData, stats))
|
||||
respond.JSON(w, http.StatusOK, model.NewPeerStats(e.cfg.Statistics.CollectPeerData, stats))
|
||||
}
|
||||
}
|
||||
|
||||
@ -260,7 +291,7 @@ func (e UserEndpoint) handleInterfacesGet() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
peers, err := e.app.GetUserInterfaces(r.Context(), domain.UserIdentifier(userId))
|
||||
peers, err := e.userService.GetUserInterfaces(r.Context(), domain.UserIdentifier(userId))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -290,7 +321,7 @@ func (e UserEndpoint) handleDelete() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
err := e.app.DeleteUser(r.Context(), domain.UserIdentifier(id))
|
||||
err := e.userService.DeleteUser(r.Context(), domain.UserIdentifier(id))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -320,7 +351,7 @@ func (e UserEndpoint) handleApiEnablePost() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
user, err := e.app.ActivateApi(r.Context(), domain.UserIdentifier(userId))
|
||||
user, err := e.userService.ActivateApi(r.Context(), domain.UserIdentifier(userId))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
@ -350,7 +381,7 @@ func (e UserEndpoint) handleApiDisablePost() http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
|
||||
user, err := e.app.DeactivateApi(r.Context(), domain.UserIdentifier(userId))
|
||||
user, err := e.userService.DeactivateApi(r.Context(), domain.UserIdentifier(userId))
|
||||
if err != nil {
|
||||
respond.JSON(w, http.StatusInternalServerError,
|
||||
model.Error{Code: http.StatusInternalServerError, Message: err.Error()})
|
||||
|
@ -79,11 +79,16 @@ func ParseServiceError(err error) (int, models.Error) {
|
||||
}
|
||||
}
|
||||
|
||||
// region handler-interfaces
|
||||
|
||||
type Authenticator interface {
|
||||
// LoggedIn checks if a user is logged in. If scopes are given, they are validated as well.
|
||||
LoggedIn(scopes ...Scope) func(next http.Handler) http.Handler
|
||||
}
|
||||
|
||||
type Validator interface {
|
||||
// Struct validates the given struct.
|
||||
Struct(s interface{}) error
|
||||
}
|
||||
|
||||
// endregion handler-interfaces
|
||||
|
Loading…
x
Reference in New Issue
Block a user