Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
G
gitlab-ce
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
1
Merge Requests
1
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
nexedi
gitlab-ce
Commits
814b0e86
Commit
814b0e86
authored
Oct 06, 2020
by
peterhegman
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Add resend invite button
Part of a larger initiative to convert the group members view from HAML to Vue
parent
b33510a2
Changes
6
Show whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
176 additions
and
2 deletions
+176
-2
app/assets/javascripts/vue_shared/components/members/action_buttons/invite_action_buttons.vue
...mponents/members/action_buttons/invite_action_buttons.vue
+5
-2
app/assets/javascripts/vue_shared/components/members/action_buttons/resend_invite_button.vue
...omponents/members/action_buttons/resend_invite_button.vue
+41
-0
app/assets/javascripts/vue_shared/components/members/table/members_table_cell.vue
...ue_shared/components/members/table/members_table_cell.vue
+4
-0
spec/frontend/vue_shared/components/members/action_buttons/invite_action_buttons_spec.js
...ents/members/action_buttons/invite_action_buttons_spec.js
+26
-0
spec/frontend/vue_shared/components/members/action_buttons/resend_invite_button_spec.js
...nents/members/action_buttons/resend_invite_button_spec.js
+66
-0
spec/frontend/vue_shared/components/members/table/member_table_cell_spec.js
...shared/components/members/table/member_table_cell_spec.js
+34
-0
No files found.
app/assets/javascripts/vue_shared/components/members/action_buttons/invite_action_buttons.vue
View file @
814b0e86
<
script
>
import
ActionButtonGroup
from
'
./action_button_group.vue
'
;
import
RemoveMemberButton
from
'
./remove_member_button.vue
'
;
import
ResendInviteButton
from
'
./resend_invite_button.vue
'
;
import
{
s__
,
sprintf
}
from
'
~/locale
'
;
export
default
{
name
:
'
InviteActionButtons
'
,
components
:
{
ActionButtonGroup
,
RemoveMemberButton
},
components
:
{
ActionButtonGroup
,
RemoveMemberButton
,
ResendInviteButton
},
props
:
{
member
:
{
type
:
Object
,
...
...
@@ -33,7 +34,9 @@ export default {
<
template
>
<action-button-group>
<!-- Resend button will go here -->
<div
v-if=
"permissions.canResend"
class=
"gl-px-1"
>
<resend-invite-button
:member-id=
"member.id"
/>
</div>
<div
v-if=
"permissions.canRemove"
class=
"gl-px-1"
>
<remove-member-button
:member-id=
"member.id"
...
...
app/assets/javascripts/vue_shared/components/members/action_buttons/resend_invite_button.vue
0 → 100644
View file @
814b0e86
<
script
>
import
{
mapState
}
from
'
vuex
'
;
import
{
GlButton
,
GlTooltipDirective
}
from
'
@gitlab/ui
'
;
import
csrf
from
'
~/lib/utils/csrf
'
;
import
{
__
}
from
'
~/locale
'
;
export
default
{
name
:
'
ResendInviteButton
'
,
csrf
,
title
:
__
(
'
Resend invite
'
),
components
:
{
GlButton
},
directives
:
{
GlTooltip
:
GlTooltipDirective
,
},
props
:
{
memberId
:
{
type
:
Number
,
required
:
true
,
},
},
computed
:
{
...
mapState
([
'
memberPath
'
]),
resendPath
()
{
return
this
.
memberPath
.
replace
(
/:id$/
,
`
${
this
.
memberId
}
/resend_invite`
);
},
},
};
</
script
>
<
template
>
<form
:action=
"resendPath"
method=
"post"
>
<input
:value=
"$options.csrf.token"
type=
"hidden"
name=
"authenticity_token"
/>
<gl-button
v-gl-tooltip
.
hover
:title=
"$options.title"
:aria-label=
"$options.title"
icon=
"paper-airplane"
type=
"submit"
/>
</form>
</
template
>
app/assets/javascripts/vue_shared/components/members/table/members_table_cell.vue
View file @
814b0e86
...
...
@@ -41,6 +41,9 @@ export default {
canRemove
()
{
return
this
.
isDirectMember
&&
this
.
member
.
canRemove
;
},
canResend
()
{
return
Boolean
(
this
.
member
.
invite
?.
canResend
);
},
},
render
()
{
return
this
.
$scopedSlots
.
default
({
...
...
@@ -49,6 +52,7 @@ export default {
isCurrentUser
:
this
.
isCurrentUser
,
permissions
:
{
canRemove
:
this
.
canRemove
,
canResend
:
this
.
canResend
,
},
});
},
...
...
spec/frontend/vue_shared/components/members/action_buttons/invite_action_buttons_spec.js
View file @
814b0e86
import
{
shallowMount
}
from
'
@vue/test-utils
'
;
import
InviteActionButtons
from
'
~/vue_shared/components/members/action_buttons/invite_action_buttons.vue
'
;
import
RemoveMemberButton
from
'
~/vue_shared/components/members/action_buttons/remove_member_button.vue
'
;
import
ResendInviteButton
from
'
~/vue_shared/components/members/action_buttons/resend_invite_button.vue
'
;
import
{
invite
as
member
}
from
'
../mock_data
'
;
describe
(
'
InviteActionButtons
'
,
()
=>
{
...
...
@@ -16,6 +17,7 @@ describe('InviteActionButtons', () => {
};
const
findRemoveMemberButton
=
()
=>
wrapper
.
find
(
RemoveMemberButton
);
const
findResendInviteButton
=
()
=>
wrapper
.
find
(
ResendInviteButton
);
afterEach
(()
=>
{
wrapper
.
destroy
();
...
...
@@ -56,4 +58,28 @@ describe('InviteActionButtons', () => {
expect
(
findRemoveMemberButton
().
exists
()).
toBe
(
false
);
});
});
describe
(
'
when user has `canResend` permissions
'
,
()
=>
{
it
(
'
renders resend invite button
'
,
()
=>
{
createComponent
({
permissions
:
{
canResend
:
true
,
},
});
expect
(
findResendInviteButton
().
exists
()).
toBe
(
true
);
});
});
describe
(
'
when user does not have `canResend` permissions
'
,
()
=>
{
it
(
'
does not render resend invite button
'
,
()
=>
{
createComponent
({
permissions
:
{
canResend
:
false
,
},
});
expect
(
findResendInviteButton
().
exists
()).
toBe
(
false
);
});
});
});
spec/frontend/vue_shared/components/members/action_buttons/resend_invite_button_spec.js
0 → 100644
View file @
814b0e86
import
{
shallowMount
,
createLocalVue
}
from
'
@vue/test-utils
'
;
import
Vuex
from
'
vuex
'
;
import
{
GlButton
}
from
'
@gitlab/ui
'
;
import
{
createMockDirective
,
getBinding
}
from
'
helpers/vue_mock_directive
'
;
import
ResendInviteButton
from
'
~/vue_shared/components/members/action_buttons/resend_invite_button.vue
'
;
jest
.
mock
(
'
~/lib/utils/csrf
'
,
()
=>
({
token
:
'
mock-csrf-token
'
}));
const
localVue
=
createLocalVue
();
localVue
.
use
(
Vuex
);
describe
(
'
ResendInviteButton
'
,
()
=>
{
let
wrapper
;
const
createStore
=
(
state
=
{})
=>
{
return
new
Vuex
.
Store
({
state
:
{
memberPath
:
'
/groups/foo-bar/-/group_members/:id
'
,
...
state
,
},
});
};
const
createComponent
=
(
propsData
=
{},
state
)
=>
{
wrapper
=
shallowMount
(
ResendInviteButton
,
{
localVue
,
store
:
createStore
(
state
),
propsData
:
{
memberId
:
1
,
...
propsData
,
},
directives
:
{
GlTooltip
:
createMockDirective
(),
},
});
};
const
findForm
=
()
=>
wrapper
.
find
(
'
form
'
);
const
findButton
=
()
=>
findForm
().
find
(
GlButton
);
beforeEach
(()
=>
{
createComponent
();
});
afterEach
(()
=>
{
wrapper
.
destroy
();
});
it
(
'
displays a tooltip
'
,
()
=>
{
expect
(
getBinding
(
findButton
().
element
,
'
gl-tooltip
'
)).
not
.
toBeUndefined
();
expect
(
findButton
().
attributes
(
'
title
'
)).
toBe
(
'
Resend invite
'
);
});
it
(
'
submits the form when button is clicked
'
,
()
=>
{
expect
(
findButton
().
attributes
(
'
type
'
)).
toBe
(
'
submit
'
);
});
it
(
'
displays form with correct action and inputs
'
,
()
=>
{
expect
(
findForm
().
attributes
(
'
action
'
)).
toBe
(
'
/groups/foo-bar/-/group_members/1/resend_invite
'
);
expect
(
findForm
()
.
find
(
'
input[name="authenticity_token"]
'
)
.
attributes
(
'
value
'
),
).
toBe
(
'
mock-csrf-token
'
);
});
});
spec/frontend/vue_shared/components/members/table/member_table_cell_spec.js
View file @
814b0e86
...
...
@@ -169,5 +169,39 @@ describe('MemberList', () => {
});
});
});
describe
(
'
canResend
'
,
()
=>
{
describe
(
'
when member type is `invite`
'
,
()
=>
{
it
(
'
returns `true` when `canResend` is `true`
'
,
()
=>
{
createComponent
({
member
:
invite
,
});
expect
(
findWrappedComponent
().
props
(
'
permissions
'
).
canResend
).
toBe
(
true
);
});
it
(
'
returns `false` when `canResend` is `false`
'
,
()
=>
{
createComponent
({
member
:
{
...
invite
,
invite
:
{
...
invite
,
canResend
:
false
,
},
},
});
expect
(
findWrappedComponent
().
props
(
'
permissions
'
).
canResend
).
toBe
(
false
);
});
});
describe
(
'
when member type is not `invite`
'
,
()
=>
{
it
(
'
returns `false`
'
,
()
=>
{
createComponent
({
member
:
memberMock
});
expect
(
findWrappedComponent
().
props
(
'
permissions
'
).
canResend
).
toBe
(
false
);
});
});
});
});
});
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment