mirror of
https://github.com/pushbits/server.git
synced 2025-06-06 12:41:59 +02:00
Implement retrieving of user data
This commit is contained in:
parent
a3de04b2a5
commit
e4e87f2710
7 changed files with 101 additions and 73 deletions
|
@ -11,28 +11,10 @@ import (
|
||||||
"github.com/gin-gonic/gin"
|
"github.com/gin-gonic/gin"
|
||||||
)
|
)
|
||||||
|
|
||||||
// The ApplicationDatabase interface for encapsulating database access.
|
|
||||||
type ApplicationDatabase interface {
|
|
||||||
CreateApplication(application *model.Application) error
|
|
||||||
DeleteApplication(application *model.Application) error
|
|
||||||
GetApplicationByID(ID uint) (*model.Application, error)
|
|
||||||
GetApplicationByToken(token string) (*model.Application, error)
|
|
||||||
GetApplications(user *model.User) ([]model.Application, error)
|
|
||||||
UpdateApplication(application *model.Application) error
|
|
||||||
|
|
||||||
GetUserByID(ID uint) (*model.User, error)
|
|
||||||
}
|
|
||||||
|
|
||||||
// The ApplicationDispatcher interface for relaying notifications.
|
|
||||||
type ApplicationDispatcher interface {
|
|
||||||
RegisterApplication(name, user string) (string, error)
|
|
||||||
DeregisterApplication(a *model.Application) error
|
|
||||||
}
|
|
||||||
|
|
||||||
// ApplicationHandler holds information for processing requests about applications.
|
// ApplicationHandler holds information for processing requests about applications.
|
||||||
type ApplicationHandler struct {
|
type ApplicationHandler struct {
|
||||||
DB ApplicationDatabase
|
DB Database
|
||||||
DP ApplicationDispatcher
|
DP Dispatcher
|
||||||
}
|
}
|
||||||
|
|
||||||
func (h *ApplicationHandler) applicationExists(token string) bool {
|
func (h *ApplicationHandler) applicationExists(token string) bool {
|
||||||
|
@ -40,20 +22,6 @@ func (h *ApplicationHandler) applicationExists(token string) bool {
|
||||||
return application != nil
|
return application != nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (h *ApplicationHandler) getApplication(ctx *gin.Context) (*model.Application, error) {
|
|
||||||
id, err := getID(ctx)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
|
|
||||||
application, err := h.DB.GetApplicationByID(id)
|
|
||||||
if success := successOrAbort(ctx, http.StatusNotFound, err); !success {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
|
|
||||||
return application, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func (h *ApplicationHandler) registerApplication(ctx *gin.Context, a *model.Application, u *model.User) error {
|
func (h *ApplicationHandler) registerApplication(ctx *gin.Context, a *model.Application, u *model.User) error {
|
||||||
log.Printf("Registering application %s.\n", a.Name)
|
log.Printf("Registering application %s.\n", a.Name)
|
||||||
|
|
||||||
|
@ -123,6 +91,9 @@ func (h *ApplicationHandler) CreateApplication(ctx *gin.Context) {
|
||||||
}
|
}
|
||||||
|
|
||||||
user := authentication.GetUser(ctx)
|
user := authentication.GetUser(ctx)
|
||||||
|
if user == nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
application, err := h.createApplication(ctx, createApplication.Name, user)
|
application, err := h.createApplication(ctx, createApplication.Name, user)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -132,10 +103,10 @@ func (h *ApplicationHandler) CreateApplication(ctx *gin.Context) {
|
||||||
ctx.JSON(http.StatusOK, &application)
|
ctx.JSON(http.StatusOK, &application)
|
||||||
}
|
}
|
||||||
|
|
||||||
// GetApplications returns all applications for the current user.
|
// GetApplications returns all applications of the current user.
|
||||||
func (h *ApplicationHandler) GetApplications(ctx *gin.Context) {
|
func (h *ApplicationHandler) GetApplications(ctx *gin.Context) {
|
||||||
user, err := getUser(ctx, h.DB)
|
user := authentication.GetUser(ctx)
|
||||||
if err != nil {
|
if user == nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -147,15 +118,15 @@ func (h *ApplicationHandler) GetApplications(ctx *gin.Context) {
|
||||||
ctx.JSON(http.StatusOK, &applications)
|
ctx.JSON(http.StatusOK, &applications)
|
||||||
}
|
}
|
||||||
|
|
||||||
// GetApplication returns all applications for the current user.
|
// GetApplication returns the application with the specified ID.
|
||||||
func (h *ApplicationHandler) GetApplication(ctx *gin.Context) {
|
func (h *ApplicationHandler) GetApplication(ctx *gin.Context) {
|
||||||
application, err := h.getApplication(ctx)
|
application, err := getApplication(ctx, h.DB)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
user, err := getUser(ctx, h.DB)
|
user := authentication.GetUser(ctx)
|
||||||
if err != nil {
|
if user == nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -170,7 +141,7 @@ func (h *ApplicationHandler) GetApplication(ctx *gin.Context) {
|
||||||
|
|
||||||
// DeleteApplication deletes an application with a certain ID.
|
// DeleteApplication deletes an application with a certain ID.
|
||||||
func (h *ApplicationHandler) DeleteApplication(ctx *gin.Context) {
|
func (h *ApplicationHandler) DeleteApplication(ctx *gin.Context) {
|
||||||
application, err := h.getApplication(ctx)
|
application, err := getApplication(ctx, h.DB)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -190,7 +161,7 @@ func (h *ApplicationHandler) DeleteApplication(ctx *gin.Context) {
|
||||||
|
|
||||||
// UpdateApplication updates an application with a certain ID.
|
// UpdateApplication updates an application with a certain ID.
|
||||||
func (h *ApplicationHandler) UpdateApplication(ctx *gin.Context) {
|
func (h *ApplicationHandler) UpdateApplication(ctx *gin.Context) {
|
||||||
application, err := h.getApplication(ctx)
|
application, err := getApplication(ctx, h.DB)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,10 +9,6 @@ import (
|
||||||
"github.com/gin-gonic/gin"
|
"github.com/gin-gonic/gin"
|
||||||
)
|
)
|
||||||
|
|
||||||
type database interface {
|
|
||||||
GetUserByID(ID uint) (*model.User, error)
|
|
||||||
}
|
|
||||||
|
|
||||||
func getID(ctx *gin.Context) (uint, error) {
|
func getID(ctx *gin.Context) (uint, error) {
|
||||||
id, ok := ctx.MustGet("id").(uint)
|
id, ok := ctx.MustGet("id").(uint)
|
||||||
if !ok {
|
if !ok {
|
||||||
|
@ -24,16 +20,30 @@ func getID(ctx *gin.Context) (uint, error) {
|
||||||
return id, nil
|
return id, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func getUser(ctx *gin.Context, db database) (*model.User, error) {
|
func getApplication(ctx *gin.Context, db Database) (*model.Application, error) {
|
||||||
id, err := getID(ctx)
|
id, err := getID(ctx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
application, err := db.GetUserByID(id)
|
application, err := db.GetApplicationByID(id)
|
||||||
if success := successOrAbort(ctx, http.StatusNotFound, err); !success {
|
if success := successOrAbort(ctx, http.StatusNotFound, err); !success {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return application, nil
|
return application, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func getUser(ctx *gin.Context, db Database) (*model.User, error) {
|
||||||
|
id, err := getID(ctx)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
user, err := db.GetUserByID(id)
|
||||||
|
if success := successOrAbort(ctx, http.StatusNotFound, err); !success {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return user, nil
|
||||||
|
}
|
||||||
|
|
34
api/interfaces.go
Normal file
34
api/interfaces.go
Normal file
|
@ -0,0 +1,34 @@
|
||||||
|
package api
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/eikendev/pushbits/model"
|
||||||
|
)
|
||||||
|
|
||||||
|
// The Database interface for encapsulating database access.
|
||||||
|
type Database interface {
|
||||||
|
CreateApplication(application *model.Application) error
|
||||||
|
DeleteApplication(application *model.Application) error
|
||||||
|
GetApplicationByID(ID uint) (*model.Application, error)
|
||||||
|
GetApplicationByToken(token string) (*model.Application, error)
|
||||||
|
UpdateApplication(application *model.Application) error
|
||||||
|
|
||||||
|
AdminUserCount() (int64, error)
|
||||||
|
CreateUser(user model.CreateUser) (*model.User, error)
|
||||||
|
DeleteUser(user *model.User) error
|
||||||
|
GetApplications(user *model.User) ([]model.Application, error)
|
||||||
|
GetUserByID(ID uint) (*model.User, error)
|
||||||
|
GetUserByName(name string) (*model.User, error)
|
||||||
|
GetUsers() ([]model.User, error)
|
||||||
|
UpdateUser(user *model.User) error
|
||||||
|
}
|
||||||
|
|
||||||
|
// The Dispatcher interface for relaying notifications.
|
||||||
|
type Dispatcher interface {
|
||||||
|
RegisterApplication(name, user string) (string, error)
|
||||||
|
DeregisterApplication(a *model.Application) error
|
||||||
|
}
|
||||||
|
|
||||||
|
// The CredentialsManager interface for updating credentials.
|
||||||
|
type CredentialsManager interface {
|
||||||
|
CreatePasswordHash(password string) []byte
|
||||||
|
}
|
48
api/user.go
48
api/user.go
|
@ -11,34 +11,12 @@ import (
|
||||||
"github.com/gin-gonic/gin"
|
"github.com/gin-gonic/gin"
|
||||||
)
|
)
|
||||||
|
|
||||||
// The UserDatabase interface for encapsulating database access.
|
|
||||||
type UserDatabase interface {
|
|
||||||
GetApplications(user *model.User) ([]model.Application, error)
|
|
||||||
|
|
||||||
AdminUserCount() (int64, error)
|
|
||||||
CreateUser(user model.CreateUser) (*model.User, error)
|
|
||||||
DeleteUser(user *model.User) error
|
|
||||||
GetUserByID(ID uint) (*model.User, error)
|
|
||||||
GetUserByName(name string) (*model.User, error)
|
|
||||||
UpdateUser(user *model.User) error
|
|
||||||
}
|
|
||||||
|
|
||||||
// The UserDispatcher interface for relaying notifications.
|
|
||||||
type UserDispatcher interface {
|
|
||||||
DeregisterApplication(a *model.Application) error
|
|
||||||
}
|
|
||||||
|
|
||||||
// The CredentialsManager interface for updating credentials.
|
|
||||||
type CredentialsManager interface {
|
|
||||||
CreatePasswordHash(password string) []byte
|
|
||||||
}
|
|
||||||
|
|
||||||
// UserHandler holds information for processing requests about users.
|
// UserHandler holds information for processing requests about users.
|
||||||
type UserHandler struct {
|
type UserHandler struct {
|
||||||
AH *ApplicationHandler
|
AH *ApplicationHandler
|
||||||
CM CredentialsManager
|
CM CredentialsManager
|
||||||
DB UserDatabase
|
DB Database
|
||||||
DP UserDispatcher
|
DP Dispatcher
|
||||||
}
|
}
|
||||||
|
|
||||||
func (h *UserHandler) userExists(name string) bool {
|
func (h *UserHandler) userExists(name string) bool {
|
||||||
|
@ -152,6 +130,28 @@ func (h *UserHandler) CreateUser(ctx *gin.Context) {
|
||||||
ctx.JSON(http.StatusOK, user.IntoExternalUser())
|
ctx.JSON(http.StatusOK, user.IntoExternalUser())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetUsers returns all users.
|
||||||
|
// This method assumes that the requesting user has privileges.
|
||||||
|
func (h *UserHandler) GetUsers(ctx *gin.Context) {
|
||||||
|
users, err := h.DB.GetUsers()
|
||||||
|
if success := successOrAbort(ctx, http.StatusInternalServerError, err); !success {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
ctx.JSON(http.StatusOK, &users)
|
||||||
|
}
|
||||||
|
|
||||||
|
// GetUser returns the user with the specified ID.
|
||||||
|
// This method assumes that the requesting user has privileges.
|
||||||
|
func (h *UserHandler) GetUser(ctx *gin.Context) {
|
||||||
|
user, err := getUser(ctx, h.DB)
|
||||||
|
if err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
ctx.JSON(http.StatusOK, user)
|
||||||
|
}
|
||||||
|
|
||||||
// DeleteUser deletes a user with a certain ID.
|
// DeleteUser deletes a user with a certain ID.
|
||||||
//
|
//
|
||||||
// This method assumes that the requesting user has privileges.
|
// This method assumes that the requesting user has privileges.
|
||||||
|
|
|
@ -24,6 +24,7 @@ func GetUser(ctx *gin.Context) *model.User {
|
||||||
user, ok := ctx.MustGet("user").(*model.User)
|
user, ok := ctx.MustGet("user").(*model.User)
|
||||||
if user == nil || !ok {
|
if user == nil || !ok {
|
||||||
ctx.AbortWithError(http.StatusInternalServerError, errors.New("an error occured while retrieving user from context"))
|
ctx.AbortWithError(http.StatusInternalServerError, errors.New("an error occured while retrieving user from context"))
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
return user
|
return user
|
||||||
|
|
|
@ -69,6 +69,15 @@ func (d *Database) GetApplications(user *model.User) ([]model.Application, error
|
||||||
return applications, err
|
return applications, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetUsers returns all users.
|
||||||
|
func (d *Database) GetUsers() ([]model.User, error) {
|
||||||
|
var users []model.User
|
||||||
|
|
||||||
|
err := d.gormdb.Find(&users).Error
|
||||||
|
|
||||||
|
return users, err
|
||||||
|
}
|
||||||
|
|
||||||
// AdminUserCount returns the number of admins or an error.
|
// AdminUserCount returns the number of admins or an error.
|
||||||
func (d *Database) AdminUserCount() (int64, error) {
|
func (d *Database) AdminUserCount() (int64, error) {
|
||||||
var users []model.User
|
var users []model.User
|
||||||
|
|
|
@ -48,6 +48,9 @@ func Create(debug bool, cm *credentials.Manager, db *database.Database, dp *disp
|
||||||
userGroup.Use(auth.RequireAdmin())
|
userGroup.Use(auth.RequireAdmin())
|
||||||
{
|
{
|
||||||
userGroup.POST("", userHandler.CreateUser)
|
userGroup.POST("", userHandler.CreateUser)
|
||||||
|
userGroup.GET("", userHandler.GetUsers)
|
||||||
|
|
||||||
|
userGroup.GET("/:id", api.RequireIDInURI(), userHandler.GetUser)
|
||||||
userGroup.DELETE("/:id", api.RequireIDInURI(), userHandler.DeleteUser)
|
userGroup.DELETE("/:id", api.RequireIDInURI(), userHandler.DeleteUser)
|
||||||
userGroup.PUT("/:id", api.RequireIDInURI(), userHandler.UpdateUser)
|
userGroup.PUT("/:id", api.RequireIDInURI(), userHandler.UpdateUser)
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue