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
0
Merge Requests
0
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
Boxiang Sun
gitlab-ce
Commits
173e27d6
Commit
173e27d6
authored
Feb 20, 2017
by
Luke "Jared" Bennett
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Finished up mattermost team creation
parent
479cdc2c
Changes
9
Hide whitespace changes
Inline
Side-by-side
Showing
9 changed files
with
289 additions
and
15 deletions
+289
-15
app/assets/javascripts/behaviors/bind_in_out.js.es6
app/assets/javascripts/behaviors/bind_in_out.js.es6
+48
-0
app/assets/javascripts/behaviors/toggler_behavior.js
app/assets/javascripts/behaviors/toggler_behavior.js
+0
-1
app/assets/javascripts/dispatcher.js.es6
app/assets/javascripts/dispatcher.js.es6
+1
-0
app/controllers/groups_controller.rb
app/controllers/groups_controller.rb
+1
-2
app/views/groups/_create_chat_team.html.haml
app/views/groups/_create_chat_team.html.haml
+9
-11
app/views/shared/_group_form.html.haml
app/views/shared/_group_form.html.haml
+2
-1
spec/features/groups_spec.rb
spec/features/groups_spec.rb
+37
-0
spec/javascripts/behaviors/bind_in_out_spec.js.es6
spec/javascripts/behaviors/bind_in_out_spec.js.es6
+189
-0
spec/javascripts/helpers/class_spec_helper.js.es6
spec/javascripts/helpers/class_spec_helper.js.es6
+2
-0
No files found.
app/assets/javascripts/behaviors/bind_in_out.js.es6
0 → 100644
View file @
173e27d6
class BindInOut {
constructor(bindIn, bindOut) {
this.in = bindIn;
this.out = bindOut;
this.eventWrapper = {};
this.eventType = /(INPUT|TEXTAREA)/.test(bindIn.tagName) ? 'keyup' : 'change';
}
addEvents() {
this.eventWrapper.updateOut = this.updateOut.bind(this);
this.in.addEventListener(this.eventType, this.eventWrapper.updateOut);
return this;
}
updateOut() {
this.out.textContent = this.in.value;
return this;
}
removeEvents() {
this.in.removeEventListener(this.eventType, this.eventWrapper.updateOut);
return this;
}
static initAll() {
const ins = document.querySelectorAll('*[data-bind-in]');
return [].map.call(ins, anIn => BindInOut.init(anIn));
}
static init(anIn, anOut) {
const out = anOut || document.querySelector(`*[data-bind-out="${anIn.dataset.bindIn}"]`);
const bindInOut = new BindInOut(anIn, out);
return bindInOut.addEvents().updateOut();
}
}
const global = window.gl || (window.gl = {});
global.BindInOut = BindInOut;
module.exports = BindInOut;
app/assets/javascripts/behaviors/toggler_behavior.js
View file @
173e27d6
...
...
@@ -22,7 +22,6 @@
// %div.js-toggle-content
//
$
(
'
body
'
).
on
(
'
click
'
,
'
.js-toggle-button
'
,
function
(
e
)
{
e
.
preventDefault
();
toggleContainer
(
$
(
this
).
closest
(
'
.js-toggle-container
'
));
});
...
...
app/assets/javascripts/dispatcher.js.es6
View file @
173e27d6
...
...
@@ -216,6 +216,7 @@ const ShortcutsBlob = require('./shortcuts_blob');
case 'admin:groups:edit':
case 'admin:groups:new':
new GroupAvatar();
gl.BindInOut.initAll();
break;
case 'projects:tree:show':
shortcut_handler = new ShortcutsNavigation();
...
...
app/controllers/groups_controller.rb
View file @
173e27d6
...
...
@@ -81,7 +81,6 @@ class GroupsController < Groups::ApplicationController
end
def
update
byebug
if
Groups
::
UpdateService
.
new
(
@group
,
current_user
,
group_params
).
execute
redirect_to
edit_group_path
(
@group
),
notice:
"Group '
#{
@group
.
name
}
' was successfully updated."
else
...
...
@@ -143,7 +142,7 @@ class GroupsController < Groups::ApplicationController
:request_access_enabled
,
:share_with_group_lock
,
:visibility_level
,
:parent_id
:parent_id
,
:create_chat_team
,
:chat_team_name
]
...
...
app/views/groups/_create_chat_team.html.haml
View file @
173e27d6
...
...
@@ -4,15 +4,13 @@
=
custom_icon
(
'icon_mattermost'
)
Mattermost
.col-sm-10
.checkbox
.checkbox
.js-toggle-container
=
f
.
label
:create_chat_team
do
=
f
.
check_box
(
:create_chat_team
,
{
checked:
@group
.
chat_team
},
'true'
,
'false'
)
Link the group to a new Mattermost team
.form-group
=
f
.
label
:chat_team
,
class:
'control-label'
do
Chat Team name
.col-sm-10
=
f
.
text_field
:chat_team
,
placeholder:
@group
.
chat_team
,
class:
'form-control mattermost-team-name'
%small
Leave blank to match your group name
.js-toggle-button
=
f
.
check_box
(
:create_chat_team
,
{
checked:
true
},
'true'
,
'false'
)
Create a Mattermost team for this group
%br
%small
.light.js-toggle-content
Team URL:
=
Settings
.
mattermost
.
host
%span
>
/
%span
{
"data-bind-out"
=>
"create_chat_team"
}
app/views/shared/_group_form.html.haml
View file @
173e27d6
...
...
@@ -18,7 +18,8 @@
=
f
.
text_field
:path
,
placeholder:
'open-source'
,
class:
'form-control'
,
autofocus:
local_assigns
[
:autofocus
]
||
false
,
required:
true
,
pattern:
Gitlab
::
Regex
::
NAMESPACE_REGEX_STR_SIMPLE
,
title:
'Please choose a group name with no special characters.'
title:
'Please choose a group name with no special characters.'
,
"data-bind-in"
=>
"
#{
'create_chat_team'
if
Gitlab
.
config
.
mattermost
.
enabled
}
"
-
if
parent
=
f
.
hidden_field
:parent_id
,
value:
parent
.
id
...
...
spec/features/groups_spec.rb
View file @
173e27d6
...
...
@@ -43,6 +43,43 @@ feature 'Group', feature: true do
expect
(
page
).
to
have_namespace_error_message
end
end
describe
'Mattermost team creation'
do
before
do
Settings
.
mattermost
[
'enabled'
]
=
mattermost_enabled
visit
new_group_path
end
context
'Mattermost enabled'
do
let
(
:mattermost_enabled
)
{
true
}
it
'displays a team creation checkbox'
do
expect
(
page
).
to
have_selector
(
'#group_create_chat_team'
)
end
it
'checks the checkbox by default'
do
expect
(
find
(
'#group_create_chat_team'
)[
'checked'
]).
to
eq
(
true
)
end
it
'updates the team URL on graph path update'
,
:js
do
out_span
=
find
(
'span[data-bind-out="create_chat_team"]'
)
expect
(
out_span
.
text
).
to
be_empty
fill_in
(
'group_path'
,
with:
'test-group'
)
expect
(
out_span
.
text
).
to
eq
(
'test-group'
)
end
end
context
'Mattermost disabled'
do
let
(
:mattermost_enabled
)
{
false
}
it
'doesnt show a team creation checkbox if Mattermost not enabled'
do
expect
(
page
).
not_to
have_selector
(
'#group_create_chat_team'
)
end
end
end
end
describe
'create a nested group'
do
...
...
spec/javascripts/behaviors/bind_in_out_spec.js.es6
0 → 100644
View file @
173e27d6
const BindInOut = require('~/behaviors/bind_in_out');
const ClassSpecHelper = require('../helpers/class_spec_helper');
describe('BindInOut', function () {
describe('.constructor', function () {
beforeEach(function () {
this.in = {};
this.out = {};
this.bindInOut = new BindInOut(this.in, this.out);
});
it('should set .in', function () {
expect(this.bindInOut.in).toBe(this.in);
});
it('should set .out', function () {
expect(this.bindInOut.out).toBe(this.out);
});
it('should set .eventWrapper', function () {
expect(this.bindInOut.eventWrapper).toEqual({});
});
describe('if .in is an input', function () {
beforeEach(function () {
this.bindInOut = new BindInOut({ tagName: 'INPUT' });
});
it('should set .eventType to keyup ', function () {
expect(this.bindInOut.eventType).toEqual('keyup');
});
});
describe('if .in is a textarea', function () {
beforeEach(function () {
this.bindInOut = new BindInOut({ tagName: 'TEXTAREA' });
});
it('should set .eventType to keyup ', function () {
expect(this.bindInOut.eventType).toEqual('keyup');
});
});
describe('if .in is not an input or textarea', function () {
beforeEach(function () {
this.bindInOut = new BindInOut({ tagName: 'SELECT' });
});
it('should set .eventType to change ', function () {
expect(this.bindInOut.eventType).toEqual('change');
});
});
});
describe('.addEvents', function () {
beforeEach(function () {
this.in = jasmine.createSpyObj('in', ['addEventListener']);
this.bindInOut = new BindInOut(this.in);
this.addEvents = this.bindInOut.addEvents();
});
it('should set .eventWrapper.updateOut', function () {
expect(this.bindInOut.eventWrapper.updateOut).toEqual(jasmine.any(Function));
});
it('should call .addEventListener', function () {
expect(this.in.addEventListener)
.toHaveBeenCalledWith(
this.bindInOut.eventType,
this.bindInOut.eventWrapper.updateOut,
);
});
it('should return the instance', function () {
expect(this.addEvents).toBe(this.bindInOut);
});
});
describe('.updateOut', function () {
beforeEach(function () {
this.in = { value: 'the-value' };
this.out = { textContent: 'not-the-value' };
this.bindInOut = new BindInOut(this.in, this.out);
this.updateOut = this.bindInOut.updateOut();
});
it('should set .out.textContent to .in.value', function () {
expect(this.out.textContent).toBe(this.in.value);
});
it('should return the instance', function () {
expect(this.updateOut).toBe(this.bindInOut);
});
});
describe('.removeEvents', function () {
beforeEach(function () {
this.in = jasmine.createSpyObj('in', ['removeEventListener']);
this.updateOut = () => {};
this.bindInOut = new BindInOut(this.in);
this.bindInOut.eventWrapper.updateOut = this.updateOut;
this.removeEvents = this.bindInOut.removeEvents();
});
it('should call .removeEventListener', function () {
expect(this.in.removeEventListener)
.toHaveBeenCalledWith(
this.bindInOut.eventType,
this.updateOut,
);
});
it('should return the instance', function () {
expect(this.removeEvents).toBe(this.bindInOut);
});
});
describe('.initAll', function () {
beforeEach(function () {
this.ins = [0, 1, 2];
this.instances = [];
spyOn(document, 'querySelectorAll').and.returnValue(this.ins);
spyOn(Array.prototype, 'map').and.callThrough();
spyOn(BindInOut, 'init');
this.initAll = BindInOut.initAll();
});
ClassSpecHelper.itShouldBeAStaticMethod(BindInOut, 'initAll');
it('should call .querySelectorAll', function () {
expect(document.querySelectorAll).toHaveBeenCalledWith('*[data-bind-in]');
});
it('should call .map', function () {
expect(Array.prototype.map).toHaveBeenCalledWith(jasmine.any(Function));
});
it('should call .init for each element', function () {
expect(BindInOut.init.calls.count()).toEqual(3);
});
it('should return an array of instances', function () {
expect(this.initAll).toEqual(jasmine.any(Array));
});
});
describe('.init', function () {
beforeEach(function () {
spyOn(BindInOut.prototype, 'addEvents').and.callFake(function () { return this; });
spyOn(BindInOut.prototype, 'updateOut').and.callFake(function () { return this; });
this.init = BindInOut.init({}, {});
});
ClassSpecHelper.itShouldBeAStaticMethod(BindInOut, 'init');
it('should call .addEvents', function () {
expect(BindInOut.prototype.addEvents).toHaveBeenCalled();
});
it('should call .updateOut', function () {
expect(BindInOut.prototype.updateOut).toHaveBeenCalled();
});
describe('if no anOut is provided', function () {
beforeEach(function () {
this.anIn = { dataset: { bindIn: 'the-data-bind-in' } };
spyOn(document, 'querySelector');
BindInOut.init(this.anIn);
});
it('should call .querySelector', function () {
expect(document.querySelector)
.toHaveBeenCalledWith(`*[data-bind-out="${this.anIn.dataset.bindIn}"]`);
});
});
});
});
spec/javascripts/helpers/class_spec_helper.js.es6
View file @
173e27d6
...
...
@@ -7,3 +7,5 @@ class ClassSpecHelper {
}
window.ClassSpecHelper = ClassSpecHelper;
module.exports = ClassSpecHelper;
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