123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264 |
- package main
- import (
- "encoding/json"
- "errors"
- "net/http"
- "strings"
- //"log"
- )
- /*
- This is the permission management module of the ArOZ Online System
- In default mode, the system only contains a user group named "administrator"
- This module also handle permission checking and others
- */
- //Initiate function for system permission
- func system_permission_service_init() {
- //Register permission configuration endpoints
- http.HandleFunc("/system/permission/listgroup", system_permission_handleListGroup)
- http.HandleFunc("/system/permission/newgroup", system_permission_createUserGroupHandler)
- http.HandleFunc("/system/permission/delgroup", system_permission_removeUserGroupHandler)
- http.HandleFunc("/system/permission/isAdmin", system_permission_handleAdminCheck)
- //http.HandleFunc("/system/permission/groupdetails", system_permission_handleGroupDetail)
- //Create table if not exists
- sysdb.NewTable("permission")
- //Register setting interface for module configuration
- registerSetting(settingModule{
- Name: "Permission Groups",
- Desc: "Handle the permission of access in groups",
- IconPath: "SystemAO/users/img/small_icon.png",
- Group: "Users",
- StartDir: "SystemAO/users/group.html",
- RequireAdmin: true,
- })
- }
- func system_permission_getUserGroups(username string) (string, error) {
- group := ""
- sysdb.Read( "auth", "group/"+username, &group)
- if group == "" {
- return "", errors.New("User group not found")
- }
- return group, nil
- }
- //Return a list of usergorup stored in the system
- func system_permission_listGroup() []string {
- groups := []string{}
- entries, _ := sysdb.ListTable("permission")
- for _, keypairs := range entries {
- if strings.Contains(string(keypairs[0]), "group/") {
- groups = append(groups, strings.Split(string(keypairs[0]), "/")[1])
- }
- }
- return groups
- }
- //Return the current list of usergroup from the database as JSON
- func system_permission_handleListGroup(w http.ResponseWriter, r *http.Request) {
- groups := []string{}
- entries, _ := sysdb.ListTable("permission")
- listPermission, _ := mv(r, "showper", false)
- if listPermission == "" {
- for _, keypairs := range entries {
- if strings.Contains(string(keypairs[0]), "group/") {
- //This is a group name record. Append the group name only.
- groups = append(groups, strings.Split(string(keypairs[0]), "/")[1])
- }
- }
- //Check if the group list is empty. If yes, create the administrator group
- if len(groups) == 0 {
- err := system_permission_createGroup("administrator", []string{"*"})
- if err != nil {
- panic("Failed to create administrator group. Is database writable?")
- }
- groups = append(groups, "administrator")
- }
- jsonString, _ := json.Marshal(groups)
- sendJSONResponse(w, string(jsonString))
- } else {
- results := map[string][]string{}
- for _, keypairs := range entries {
- if strings.Contains(string(keypairs[0]), "group/") {
- //This is a group name record. Append the group name only.
- thisGroupPermission := []string{}
- json.Unmarshal(keypairs[1], &thisGroupPermission)
- results[strings.Split(string(keypairs[0]), "/")[1]] = thisGroupPermission
- }
- }
- jsonString, _ := json.Marshal(results)
- sendJSONResponse(w, string(jsonString))
- }
- /*
- //Deprecated method for listing group with JSON string storage
- groupsData := "";
- sysdb.Read( "permission", "groups", &groups)
- //There are always at least one group and this key must be valid. Not need to check for error.
- w.Header().Set("Content-Type", "application/json")
- sendTextResponse(w,groups)
- */
- }
- func system_permission_handleAdminCheck(w http.ResponseWriter, r *http.Request) {
- isAdmin := system_permission_checkUserIsAdmin(w, r)
- if isAdmin {
- sendJSONResponse(w, "true")
- } else {
- sendJSONResponse(w, "false")
- }
- }
- func system_permission_handleGroupDetail(w http.ResponseWriter, r *http.Request) {
- opr, _ := mv(r, "opr", false)
- if opr == "" {
- //List all groups with detail
- var groupsRaw []byte
- sysdb.Read( "permission", "groups", &groupsRaw)
- var groups []string
- json.Unmarshal(groupsRaw, &groups)
- }
- }
- func system_permission_createGroup(groupname string, modulepermission []string) error {
- //Check if group already exists
- if !system_permission_groupExists(groupname) {
- //This group do not exists. Continue to create
- err := sysdb.Write("permission", "group/"+groupname, modulepermission)
- if err != nil {
- return err
- }
- } else {
- //This group exists.
- return errors.New("Group already exists")
- }
- return nil
- }
- func system_permission_removeUserGroupHandler(w http.ResponseWriter, r *http.Request) {
- //Check if user is admin
- isAdmin := system_permission_checkUserIsAdmin(w, r)
- if !isAdmin {
- sendErrorResponse(w, "Permission denied")
- return
- }
- //Check if the groupname is provided
- groupname, err := mv(r, "groupname", false)
- if err != nil {
- sendErrorResponse(w, "Groupname not defined")
- return
- }
- //Remove the group from database
- if system_permission_groupExists(groupname) {
- //This group exits. Continue removal
- err := sysdb.Delete("permission", "group/"+groupname)
- if err != nil {
- sendErrorResponse(w, err.Error())
- return
- }
- } else {
- //This group exists.
- sendErrorResponse(w, "Given group not exists")
- return
- }
- sendOK(w)
- }
- func system_permission_createUserGroupHandler(w http.ResponseWriter, r *http.Request) {
- isAdmin := system_permission_checkUserIsAdmin(w, r)
- if !isAdmin {
- sendErrorResponse(w, "Permission denied")
- return
- }
- groupname, err := mv(r, "groupname", true)
- if err != nil {
- sendErrorResponse(w, "Groupname not defined")
- return
- }
- permissions, err := mv(r, "permission", true)
- if err != nil {
- sendErrorResponse(w, "Permission not defined")
- return
- }
- permissionList := []string{}
- err = json.Unmarshal([]byte(permissions), &permissionList)
- if err != nil {
- sendErrorResponse(w, "Failed to parse the permission list")
- return
- }
- system_permission_createGroup(groupname, permissionList)
- sendOK(w)
- }
- func system_permission_getGroupAccessList(groupname string) []string {
- moduleList := []string{}
- err := sysdb.Read( "permission", "group/"+groupname, &moduleList)
- if err != nil {
- return []string{}
- }
- return moduleList
- }
- func system_permission_checkUserHasAccessToModule(username string, modulename string) bool {
- //Get user group and see if group exists.
- usergroup := system_permission_getUserPermissionGroup(username)
- groupExists := system_permission_groupExists(usergroup)
- if !groupExists {
- return false
- }
- //Group exists. Check permission on module
- groupAccessList := system_permission_getGroupAccessList(usergroup)
- if len(groupAccessList) == 1 && groupAccessList[0] == "*" {
- return true
- }
- if stringInSlice(modulename, groupAccessList) {
- return true
- }
- return false
- }
- func system_permission_checkUserIsAdmin(w http.ResponseWriter, r *http.Request) bool {
- username, err := authAgent.GetUserName(w, r)
- if err != nil{
- return false
- }
- userGroup := system_permission_getUserPermissionGroup(username)
- if userGroup == "administrator" {
- return true
- }
- return false
- }
- func system_permission_getUserPermissionGroup(username string) string {
- usergroup := ""
- sysdb.Read( "auth", "group/"+username, &usergroup)
- return (usergroup)
- }
- //This function check if the given usergroup ID exists.
- func system_permission_groupExists(group string) bool {
- dummyPermission := []string{}
- err := sysdb.Read( "permission", "group/"+group, &dummyPermission)
- if err != nil || len(dummyPermission) == 0 {
- return false
- }
- return true
- }
|