Skip to content

Commit

Permalink
Merge pull request #171 from ctreminiom/feature/user-permission-endpoint
Browse files Browse the repository at this point in the history
Enabled the possibility to check the user permissions using the permi…
  • Loading branch information
ctreminiom authored Mar 2, 2023
2 parents 519754a + 09ab86c commit 23e1ad2
Show file tree
Hide file tree
Showing 4 changed files with 255 additions and 2 deletions.
62 changes: 60 additions & 2 deletions jira/internal/user_search_impl.go
Original file line number Diff line number Diff line change
Expand Up @@ -40,12 +40,11 @@ func (u *UserSearchService) Projects(ctx context.Context, accountId string, proj

// Do return a list of users that match the search string and property.
//
//
// This operation takes the users in the range defined by startAt and maxResults, up to the thousandth user,
//
// and then returns only the users from that range that match the search string and property.
//
// This means the operation usually returns fewer users than specified in maxResults
// # This means the operation usually returns fewer users than specified in maxResults
//
// GET /rest/api/{2-3}/user/search
//
Expand All @@ -54,11 +53,70 @@ func (u *UserSearchService) Do(ctx context.Context, accountId, query string, sta
return u.internalClient.Do(ctx, accountId, query, startAt, maxResults)
}

// Check returns a list of users who fulfill these criteria:
//
// 1. their user attributes match a search string.
// 2. they have a set of permissions for a project or issue.
//
// If no search string is provided, a list of all users with the permissions is returned.
//
// GET /rest/api/{2-3}/user/permission/search
//
// https://docs.go-atlassian.io/jira-software-cloud/users/search#find-users-with-permissions
func (u *UserSearchService) Check(ctx context.Context, permission string, options *model.UserPermissionCheckParamsScheme, startAt, maxResults int) ([]*model.UserScheme, *model.ResponseScheme, error) {
return u.internalClient.Check(ctx, permission, options, startAt, maxResults)
}

type internalUserSearchImpl struct {
c service.Client
version string
}

func (i *internalUserSearchImpl) Check(ctx context.Context, permission string, options *model.UserPermissionCheckParamsScheme, startAt, maxResults int) ([]*model.UserScheme, *model.ResponseScheme, error) {

if permission == "" {
return nil, nil, model.ErrNoPermissionGrantIDError
}

params := url.Values{}
params.Add("startAt", strconv.Itoa(startAt))
params.Add("maxResults", strconv.Itoa(maxResults))

if options != nil {

if options.Query != "" {
params.Add("query", options.Query)
}

if options.AccountID != "" {
params.Add("accountId", options.AccountID)
}

if options.IssueKey != "" {
params.Add("issueKey", options.IssueKey)
}

if options.ProjectKey != "" {
params.Add("projectKey", options.ProjectKey)
}
}

endpoint := fmt.Sprintf("rest/api/%v/user/permission/search?%v", i.version, params.Encode())

request, err := i.c.NewRequest(ctx, http.MethodGet, endpoint, nil)
if err != nil {
return nil, nil, err
}

var users []*model.UserScheme
response, err := i.c.Call(request, &users)
if err != nil {
return nil, response, err
}

return users, response, nil
}

func (i *internalUserSearchImpl) Projects(ctx context.Context, accountId string, projectKeys []string, startAt, maxResults int) ([]*model.UserScheme, *model.ResponseScheme, error) {

if len(projectKeys) == 0 {
Expand Down
175 changes: 175 additions & 0 deletions jira/internal/user_search_impl_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -314,3 +314,178 @@ func Test_internalUserSearchImpl_Do(t *testing.T) {
})
}
}

func Test_internalUserSearchImpl_Check(t *testing.T) {

type fields struct {
c service.Client
version string
}

type args struct {
ctx context.Context
permission string
options *model.UserPermissionCheckParamsScheme
startAt, maxResults int
}

testCases := []struct {
name string
fields fields
args args
on func(*fields)
wantErr bool
Err error
}{
{
name: "when the api version is v3",
fields: fields{version: "3"},
args: args{
ctx: context.TODO(),
permission: "CREATE_ISSUES",
options: &model.UserPermissionCheckParamsScheme{
Query: "project A",
AccountID: "uuid-sample",
IssueKey: "DFUMM-1",
ProjectKey: "DUMMY",
},
startAt: 100,
maxResults: 50,
},
on: func(fields *fields) {

client := mocks.NewClient(t)

client.On("NewRequest",
context.Background(),
http.MethodGet,
"rest/api/3/user/permission/search?accountId=uuid-sample&issueKey=DFUMM-1&maxResults=50&projectKey=DUMMY&query=project+A&startAt=100",
nil).
Return(&http.Request{}, nil)

client.On("Call",
&http.Request{},
mock.Anything).
Return(&model.ResponseScheme{}, nil)

fields.c = client
},
wantErr: false,
Err: nil,
},

{
name: "when the permission grant is not provided",
fields: fields{version: "3"},
args: args{
ctx: context.TODO(),
},
on: func(fields *fields) {
client := mocks.NewClient(t)
fields.c = client
},
wantErr: true,
Err: model.ErrNoPermissionGrantIDError,
},

{
name: "when the api version is v2",
fields: fields{version: "2"},
args: args{
ctx: context.TODO(),
permission: "CREATE_ISSUES",
options: &model.UserPermissionCheckParamsScheme{
Query: "project A",
AccountID: "uuid-sample",
IssueKey: "DFUMM-1",
ProjectKey: "DUMMY",
},
startAt: 100,
maxResults: 50,
},
on: func(fields *fields) {

client := mocks.NewClient(t)

client.On("NewRequest",
context.Background(),
http.MethodGet,
"rest/api/2/user/permission/search?accountId=uuid-sample&issueKey=DFUMM-1&maxResults=50&projectKey=DUMMY&query=project+A&startAt=100",
nil).
Return(&http.Request{}, nil)

client.On("Call",
&http.Request{},
mock.Anything).
Return(&model.ResponseScheme{}, nil)

fields.c = client
},
wantErr: false,
Err: nil,
},

{
name: "when the http request cannot be created",
fields: fields{version: "3"},
args: args{
ctx: context.TODO(),
permission: "CREATE_ISSUES",
options: &model.UserPermissionCheckParamsScheme{
Query: "project A",
AccountID: "uuid-sample",
IssueKey: "DFUMM-1",
ProjectKey: "DUMMY",
},
startAt: 100,
maxResults: 50,
},
on: func(fields *fields) {

client := mocks.NewClient(t)

client.On("NewRequest",
context.Background(),
http.MethodGet,
"rest/api/3/user/permission/search?accountId=uuid-sample&issueKey=DFUMM-1&maxResults=50&projectKey=DUMMY&query=project+A&startAt=100",
nil).
Return(&http.Request{}, errors.New("error, unable to create the http request"))

fields.c = client
},
wantErr: true,
Err: errors.New("error, unable to create the http request"),
},
}

for _, testCase := range testCases {
t.Run(testCase.name, func(t *testing.T) {

if testCase.on != nil {
testCase.on(&testCase.fields)
}

newService, err := NewUserSearchService(testCase.fields.c, testCase.fields.version)
assert.NoError(t, err)

gotResult, gotResponse, err := newService.Check(testCase.args.ctx, testCase.args.permission, testCase.args.options,
testCase.args.startAt, testCase.args.maxResults)

if testCase.wantErr {

if err != nil {
t.Logf("error returned: %v", err.Error())
}

assert.EqualError(t, err, testCase.Err.Error())

} else {

assert.NoError(t, err)
assert.NotEqual(t, gotResponse, nil)
assert.NotEqual(t, gotResult, nil)
}

})
}
}
7 changes: 7 additions & 0 deletions pkg/infra/models/jira_user.go
Original file line number Diff line number Diff line change
Expand Up @@ -52,3 +52,10 @@ type UserSearchPageScheme struct {
IsLast bool `json:"isLast,omitempty"`
Values []*UserScheme `json:"values,omitempty"`
}

type UserPermissionCheckParamsScheme struct {
Query string
AccountID string
IssueKey string
ProjectKey string
}
13 changes: 13 additions & 0 deletions service/jira/user.go
Original file line number Diff line number Diff line change
Expand Up @@ -88,4 +88,17 @@ type UserSearchConnector interface {
//
// https://docs.go-atlassian.io/jira-software-cloud/users/search#find-users
Do(ctx context.Context, accountId, query string, startAt, maxResults int) ([]*model.UserScheme, *model.ResponseScheme, error)

// Check returns a list of users who fulfill these criteria:
//
// 1. their user attributes match a search string.
// 2. they have a set of permissions for a project or issue.
//
//
// If no search string is provided, a list of all users with the permissions is returned.
//
// GET /rest/api/{2-3}/user/permission/search
//
// https://docs.go-atlassian.io/jira-software-cloud/users/search#find-users-with-permissions
Check(ctx context.Context, permission string, options *model.UserPermissionCheckParamsScheme, startAt, maxResults int) ([]*model.UserScheme, *model.ResponseScheme, error)
}

0 comments on commit 23e1ad2

Please sign in to comment.