add support to update permissions
All checks were successful
continuous-integration/drone/push Build is passing
All checks were successful
continuous-integration/drone/push Build is passing
This commit is contained in:
20
README.md
20
README.md
@@ -224,7 +224,7 @@ Delete permission by specifying description
|
||||
Body
|
||||
```
|
||||
{
|
||||
"Description":"Readonly access to default safe"
|
||||
"Description": "Readonly access to default safe"
|
||||
|
||||
}
|
||||
```
|
||||
@@ -234,7 +234,7 @@ Delete permission by specifying permission id
|
||||
Body
|
||||
```
|
||||
{
|
||||
"permissionId":2
|
||||
"permissionId": 2
|
||||
|
||||
}
|
||||
```
|
||||
@@ -243,6 +243,22 @@ Deletes a permission mapping either a user or a group to a safe. Either the perm
|
||||
|
||||
Deleting a permission should be performed prior to deleting any groups specified in that permission.
|
||||
|
||||
#### Update Permission
|
||||
**POST** `/api/admin/permission/update`
|
||||
|
||||
Change description of permission
|
||||
|
||||
Body
|
||||
```
|
||||
{
|
||||
"permissionId": 2
|
||||
"Description": "New Permission Description"
|
||||
|
||||
}
|
||||
```
|
||||
|
||||
Updates an existing permission. The permissionId must be specified. This operation can only be performed by a user that is admin enabled.
|
||||
|
||||
### Group Operations
|
||||
|
||||
#### List Groups
|
||||
|
@@ -6,6 +6,7 @@ import (
|
||||
"log"
|
||||
"net/http"
|
||||
"smt/models"
|
||||
"smt/utils"
|
||||
"strings"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
@@ -173,3 +174,80 @@ func DeletePermissionHandler(c *gin.Context) {
|
||||
c.JSON(http.StatusOK, gin.H{"message": "permission deletion success"})
|
||||
}
|
||||
}
|
||||
|
||||
func UpdatePermissionHandler(c *gin.Context) {
|
||||
var input PermissionInput
|
||||
var RequestingUserId int
|
||||
|
||||
if err := c.ShouldBindJSON(&input); err != nil {
|
||||
c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
|
||||
return
|
||||
}
|
||||
|
||||
// Input validation
|
||||
if input.PermissionId == 0 {
|
||||
errString := "must specify permission id"
|
||||
log.Printf("UpdatePermissionHandler %s\n", errString)
|
||||
c.JSON(http.StatusBadRequest, gin.H{"error": errString})
|
||||
return
|
||||
}
|
||||
|
||||
if val, ok := c.Get("user-id"); !ok {
|
||||
c.JSON(http.StatusBadRequest, gin.H{"error": "error determining user"})
|
||||
return
|
||||
} else {
|
||||
RequestingUserId = val.(int)
|
||||
}
|
||||
|
||||
// Check specified permission currently exists
|
||||
currentPermission, err := models.PermissionGetById(input.PermissionId)
|
||||
|
||||
if err != nil {
|
||||
errString := fmt.Sprintf("error querying existing permission : '%s'", err)
|
||||
log.Printf("UpdatePermissionHandler %s\n", errString)
|
||||
c.JSON(http.StatusBadRequest, gin.H{"error": errString})
|
||||
return
|
||||
}
|
||||
if (models.Permission{} == currentPermission) {
|
||||
errString := fmt.Sprintf("no permission id '%d' found", input.PermissionId)
|
||||
log.Printf("UpdatePermissionHandler %s\n", errString)
|
||||
c.JSON(http.StatusBadRequest, gin.H{"error": errString})
|
||||
return
|
||||
}
|
||||
|
||||
// create new struct with values supplied by user
|
||||
newPermission := models.Permission{
|
||||
PermissionId: input.PermissionId,
|
||||
Description: input.Description,
|
||||
ReadOnly: input.ReadOnly,
|
||||
SafeId: input.SafeId,
|
||||
UserId: input.UserId,
|
||||
GroupId: input.GroupId,
|
||||
}
|
||||
|
||||
//remove leading/trailing spaces in permission description
|
||||
newPermission.Description = html.EscapeString(strings.TrimSpace(newPermission.Description))
|
||||
|
||||
// Copy newPermission into currentPermission
|
||||
utils.UpdateStruct(¤tPermission, &newPermission)
|
||||
|
||||
// run the database update
|
||||
_, err = currentPermission.PermissionUpdate()
|
||||
|
||||
if err != nil {
|
||||
errString := fmt.Sprintf("error updating permission : '%s'", err)
|
||||
log.Printf("UpdatePermissionHandler %s\n", errString)
|
||||
c.JSON(http.StatusBadRequest, gin.H{"error": errString})
|
||||
return
|
||||
}
|
||||
|
||||
//create audit record
|
||||
a := models.Audit{
|
||||
UserId: RequestingUserId,
|
||||
IpAddress: c.ClientIP(),
|
||||
EventText: fmt.Sprintf("Updated Permission '%s' with id %d", currentPermission.Description, currentPermission.PermissionId),
|
||||
}
|
||||
a.AuditLogAdd()
|
||||
|
||||
c.JSON(http.StatusOK, gin.H{"message": "permission update success"})
|
||||
}
|
||||
|
1
main.go
1
main.go
@@ -263,6 +263,7 @@ func main() {
|
||||
adminOnly.GET("/permissions", controllers.GetPermissionsHandler)
|
||||
adminOnly.POST("/permission/add", controllers.AddPermissionHandler)
|
||||
adminOnly.POST("/permission/delete", controllers.DeletePermissionHandler)
|
||||
adminOnly.POST("/permission/update", controllers.UpdatePermissionHandler)
|
||||
|
||||
// Safe functions for admin
|
||||
adminOnly.GET("/safe/listall", controllers.GetAllSafesHandler)
|
||||
|
@@ -142,3 +142,29 @@ func (p *Permission) PermissionDelete() error {
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// PermissionUpdate updates an existing permission definition in the database
|
||||
func (p *Permission) PermissionUpdate() (*Permission, error) {
|
||||
|
||||
var err error
|
||||
|
||||
log.Printf("PermissionUpdate storing values '%v'\n", p)
|
||||
|
||||
if p.PermissionId == 0 {
|
||||
err = errors.New("PermissionUpdate unable to update permission with empty PermissionId field")
|
||||
log.Printf("PermissionUpdate error in pre-check : '%s'\n", err)
|
||||
return p, err
|
||||
}
|
||||
|
||||
result, err := db.NamedExec((`UPDATE permissions SET Description = :Description, ReadOnly = :ReadOnly, SafeId = :SafeId, UserId = :UserId, GroupId = :GroupId WHERE PermissionId = :PermissionId`), p)
|
||||
if err != nil {
|
||||
log.Printf("PermissionUpdate error executing sql record : '%s'\n", err)
|
||||
return &Permission{}, err
|
||||
} else {
|
||||
affected, _ := result.RowsAffected()
|
||||
id, _ := result.LastInsertId()
|
||||
log.Printf("PermissionUpdate returned result id '%d' affecting %d row(s).\n", id, affected)
|
||||
}
|
||||
|
||||
return p, nil
|
||||
}
|
||||
|
@@ -102,3 +102,20 @@ func AppendIfNotExists[T Identifiable](slice []T, element T) []T {
|
||||
// Element with the same Id does not exist, append the new element
|
||||
return append(slice, element)
|
||||
}
|
||||
|
||||
// UpdateStruct updates the values in the destination struct with values from the source struct
|
||||
func UpdateStruct(dest interface{}, src interface{}) {
|
||||
destValue := reflect.ValueOf(dest).Elem()
|
||||
srcValue := reflect.ValueOf(src).Elem()
|
||||
|
||||
destType := destValue.Type()
|
||||
|
||||
for i := 0; i < srcValue.NumField(); i++ {
|
||||
srcField := srcValue.Field(i)
|
||||
|
||||
destField := destValue.FieldByName(destType.Field(i).Name)
|
||||
if destField.IsValid() && destField.Type() == srcField.Type() && destField.CanSet() {
|
||||
destField.Set(srcField)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user