github.com/gigforks/mattermost-server@v4.9.1-0.20180619094218-800d97fa55d0+incompatible/app/authorization.go (about)

     1  // Copyright (c) 2016-present Mattermost, Inc. All Rights Reserved.
     2  // See License.txt for license information.
     3  
     4  package app
     5  
     6  import (
     7  	"fmt"
     8  	"net/http"
     9  	"strings"
    10  
    11  	"github.com/mattermost/mattermost-server/mlog"
    12  	"github.com/mattermost/mattermost-server/model"
    13  )
    14  
    15  func (a *App) SessionHasPermissionTo(session model.Session, permission *model.Permission) bool {
    16  	return a.RolesGrantPermission(session.GetUserRoles(), permission.Id)
    17  }
    18  
    19  /// DO NOT USE: LEGACY
    20  func (a *App) SessionHasPermissionToTeam(session model.Session, teamId string, permission *model.Permission) bool {
    21  	if teamId == "" {
    22  		return false
    23  	}
    24  
    25  	teamMember := session.GetTeamByTeamId(teamId)
    26  	if teamMember != nil {
    27  		if a.RolesGrantPermission(teamMember.GetRoles(), permission.Id) {
    28  			return true
    29  		}
    30  	}
    31  
    32  	return a.RolesGrantPermission(session.GetUserRoles(), permission.Id)
    33  }
    34  
    35  func (a *App) SessionHasPermissionToChannel(session model.Session, channelId string, permission *model.Permission) bool {
    36  	if channelId == "" {
    37  		return false
    38  	}
    39  
    40  	cmc := a.Srv.Store.Channel().GetAllChannelMembersForUser(session.UserId, true)
    41  
    42  	var channelRoles []string
    43  	if cmcresult := <-cmc; cmcresult.Err == nil {
    44  		ids := cmcresult.Data.(map[string]string)
    45  		if roles, ok := ids[channelId]; ok {
    46  			channelRoles = strings.Fields(roles)
    47  			if a.RolesGrantPermission(channelRoles, permission.Id) {
    48  				return true
    49  			}
    50  		}
    51  	}
    52  
    53  	channel, err := a.GetChannel(channelId)
    54  	if err == nil && channel.TeamId != "" {
    55  		return a.SessionHasPermissionToTeam(session, channel.TeamId, permission)
    56  	} else if err != nil && err.StatusCode == http.StatusNotFound {
    57  		return false
    58  	}
    59  
    60  	return a.SessionHasPermissionTo(session, permission)
    61  }
    62  
    63  func (a *App) SessionHasPermissionToChannelByPost(session model.Session, postId string, permission *model.Permission) bool {
    64  	var channelMember *model.ChannelMember
    65  	if result := <-a.Srv.Store.Channel().GetMemberForPost(postId, session.UserId); result.Err == nil {
    66  		channelMember = result.Data.(*model.ChannelMember)
    67  
    68  		if a.RolesGrantPermission(channelMember.GetRoles(), permission.Id) {
    69  			return true
    70  		}
    71  	}
    72  
    73  	if result := <-a.Srv.Store.Channel().GetForPost(postId); result.Err == nil {
    74  		channel := result.Data.(*model.Channel)
    75  		return a.SessionHasPermissionToTeam(session, channel.TeamId, permission)
    76  	}
    77  
    78  	return a.SessionHasPermissionTo(session, permission)
    79  }
    80  
    81  func (a *App) SessionHasPermissionToUser(session model.Session, userId string) bool {
    82  	if userId == "" {
    83  		return false
    84  	}
    85  
    86  	if session.UserId == userId {
    87  		return true
    88  	}
    89  
    90  	if a.SessionHasPermissionTo(session, model.PERMISSION_EDIT_OTHER_USERS) {
    91  		return true
    92  	}
    93  
    94  	return false
    95  }
    96  
    97  func (a *App) SessionHasPermissionToPost(session model.Session, postId string, permission *model.Permission) bool {
    98  	post, err := a.GetSinglePost(postId)
    99  	if err != nil {
   100  		return false
   101  	}
   102  
   103  	if post.UserId == session.UserId {
   104  		return true
   105  	}
   106  
   107  	return a.SessionHasPermissionToChannel(session, post.ChannelId, permission)
   108  }
   109  
   110  func (a *App) HasPermissionTo(askingUserId string, permission *model.Permission) bool {
   111  	user, err := a.GetUser(askingUserId)
   112  	if err != nil {
   113  		return false
   114  	}
   115  
   116  	roles := user.GetRoles()
   117  
   118  	return a.RolesGrantPermission(roles, permission.Id)
   119  }
   120  
   121  func (a *App) HasPermissionToTeam(askingUserId string, teamId string, permission *model.Permission) bool {
   122  	if teamId == "" || askingUserId == "" {
   123  		return false
   124  	}
   125  
   126  	teamMember, err := a.GetTeamMember(teamId, askingUserId)
   127  	if err != nil {
   128  		return false
   129  	}
   130  
   131  	roles := teamMember.GetRoles()
   132  
   133  	if a.RolesGrantPermission(roles, permission.Id) {
   134  		return true
   135  	}
   136  
   137  	return a.HasPermissionTo(askingUserId, permission)
   138  }
   139  
   140  func (a *App) HasPermissionToChannel(askingUserId string, channelId string, permission *model.Permission) bool {
   141  	if channelId == "" || askingUserId == "" {
   142  		return false
   143  	}
   144  
   145  	channelMember, err := a.GetChannelMember(channelId, askingUserId)
   146  	if err == nil {
   147  		roles := channelMember.GetRoles()
   148  		if a.RolesGrantPermission(roles, permission.Id) {
   149  			return true
   150  		}
   151  	}
   152  
   153  	var channel *model.Channel
   154  	channel, err = a.GetChannel(channelId)
   155  	if err == nil {
   156  		return a.HasPermissionToTeam(askingUserId, channel.TeamId, permission)
   157  	}
   158  
   159  	return a.HasPermissionTo(askingUserId, permission)
   160  }
   161  
   162  func (a *App) HasPermissionToChannelByPost(askingUserId string, postId string, permission *model.Permission) bool {
   163  	var channelMember *model.ChannelMember
   164  	if result := <-a.Srv.Store.Channel().GetMemberForPost(postId, askingUserId); result.Err == nil {
   165  		channelMember = result.Data.(*model.ChannelMember)
   166  
   167  		if a.RolesGrantPermission(channelMember.GetRoles(), permission.Id) {
   168  			return true
   169  		}
   170  	}
   171  
   172  	if result := <-a.Srv.Store.Channel().GetForPost(postId); result.Err == nil {
   173  		channel := result.Data.(*model.Channel)
   174  		return a.HasPermissionToTeam(askingUserId, channel.TeamId, permission)
   175  	}
   176  
   177  	return a.HasPermissionTo(askingUserId, permission)
   178  }
   179  
   180  func (a *App) HasPermissionToUser(askingUserId string, userId string) bool {
   181  	if askingUserId == userId {
   182  		return true
   183  	}
   184  
   185  	if a.HasPermissionTo(askingUserId, model.PERMISSION_EDIT_OTHER_USERS) {
   186  		return true
   187  	}
   188  
   189  	return false
   190  }
   191  
   192  func (a *App) RolesGrantPermission(roleNames []string, permissionId string) bool {
   193  	roles, err := a.GetRolesByNames(roleNames)
   194  	if err != nil {
   195  		// This should only happen if something is very broken. We can't realistically
   196  		// recover the situation, so deny permission and log an error.
   197  		mlog.Error("Failed to get roles from database with role names: " + strings.Join(roleNames, ","))
   198  		mlog.Error(fmt.Sprint(err))
   199  		return false
   200  	}
   201  
   202  	for _, role := range roles {
   203  		permissions := role.Permissions
   204  		for _, permission := range permissions {
   205  			if permission == permissionId {
   206  				return true
   207  			}
   208  		}
   209  	}
   210  
   211  	return false
   212  }