Support leaving a team
TNL-1910
This commit is contained in:
@@ -284,6 +284,11 @@ class TeamPage(CoursePage, PaginatedUIMixin):
|
||||
"""Verifies that team leave link is present"""
|
||||
return self.q(css='.leave-team-link').present
|
||||
|
||||
def click_leave_team_link(self):
|
||||
""" Click on Leave Team link"""
|
||||
self.q(css='.leave-team-link').first.click()
|
||||
self.wait_for_ajax()
|
||||
|
||||
@property
|
||||
def team_invite_section_present(self):
|
||||
"""Verifies that invite section is present"""
|
||||
@@ -334,3 +339,8 @@ class TeamPage(CoursePage, PaginatedUIMixin):
|
||||
def join_team_message_present(self):
|
||||
""" Returns True if Join Team message is present else False """
|
||||
return self.q(css='.join-team .join-team-message').present
|
||||
|
||||
@property
|
||||
def new_post_button_present(self):
|
||||
""" Returns True if New Post button is present else False """
|
||||
return self.q(css='.discussion-module .new-post-btn').present
|
||||
|
||||
@@ -750,6 +750,9 @@ class CreateTeamTest(TeamsTabBase):
|
||||
@ddt.ddt
|
||||
class TeamPageTest(TeamsTabBase):
|
||||
"""Tests for viewing a specific team"""
|
||||
|
||||
SEND_INVITE_TEXT = 'Send this link to friends so that they can join too.'
|
||||
|
||||
def setUp(self):
|
||||
super(TeamPageTest, self).setUp()
|
||||
self.topic = {u"name": u"Example Topic", u"id": "example_topic", u"description": "Description"}
|
||||
@@ -900,10 +903,12 @@ class TeamPageTest(TeamsTabBase):
|
||||
self.assertTrue(self.team_page.team_leave_link_present)
|
||||
self.assertTrue(self.team_page.team_invite_section_present)
|
||||
self.assertEqual(self.team_page.team_invite_help_text, invite_text)
|
||||
self.assertTrue(self.team_page.new_post_button_present)
|
||||
else:
|
||||
self.assertEqual(self.team_page.team_user_membership_text, '')
|
||||
self.assertFalse(self.team_page.team_leave_link_present)
|
||||
self.assertFalse(self.team_page.team_invite_section_present)
|
||||
self.assertFalse(self.team_page.new_post_button_present)
|
||||
|
||||
def test_team_member_can_see_full_team_details(self):
|
||||
"""
|
||||
@@ -922,7 +927,7 @@ class TeamPageTest(TeamsTabBase):
|
||||
|
||||
self.assert_team_details(
|
||||
num_members=1,
|
||||
invite_text='Send this link to friends so that they can join too.'
|
||||
invite_text=self.SEND_INVITE_TEXT
|
||||
)
|
||||
|
||||
def test_other_users_can_see_limited_team_details(self):
|
||||
@@ -994,7 +999,7 @@ class TeamPageTest(TeamsTabBase):
|
||||
|
||||
self.assert_team_details(
|
||||
num_members=1,
|
||||
invite_text='Send this link to friends so that they can join too.'
|
||||
invite_text=self.SEND_INVITE_TEXT
|
||||
)
|
||||
self.assertEqual(self.team_page.team_invite_url, '{0}?invite=true'.format(self.team_page.url))
|
||||
|
||||
@@ -1006,9 +1011,11 @@ class TeamPageTest(TeamsTabBase):
|
||||
and a team belonging to that topic
|
||||
And I visit the Team page for that team
|
||||
Then I should see Join Team button
|
||||
And I should not see New Post button
|
||||
When I click on Join Team button
|
||||
Then there should be no Join Team button and no message
|
||||
And I should see the updated information under Team Details
|
||||
And I should see New Post button
|
||||
"""
|
||||
self._set_team_configuration_and_membership(create_membership=False)
|
||||
self.team_page.visit()
|
||||
@@ -1016,7 +1023,7 @@ class TeamPageTest(TeamsTabBase):
|
||||
self.team_page.click_join_team_button()
|
||||
self.assertFalse(self.team_page.join_team_button_present)
|
||||
self.assertFalse(self.team_page.join_team_message_present)
|
||||
self.assert_team_details(num_members=1, invite_text='Send this link to friends so that they can join too.')
|
||||
self.assert_team_details(num_members=1, is_member=True, invite_text=self.SEND_INVITE_TEXT)
|
||||
|
||||
def test_already_member_message(self):
|
||||
"""
|
||||
@@ -1055,3 +1062,27 @@ class TeamPageTest(TeamsTabBase):
|
||||
self.team_page.visit()
|
||||
self.assertEqual(self.team_page.join_team_message, 'This team is full.')
|
||||
self.assert_team_details(num_members=1, is_member=False, max_size=1)
|
||||
|
||||
def test_leave_team(self):
|
||||
"""
|
||||
Scenario: User can leave a team.
|
||||
|
||||
Given I am enrolled in a course with a team configuration, a topic,
|
||||
and a team belonging to that topic
|
||||
And I am a member of team
|
||||
And I visit the team
|
||||
And I should not see Join Team button
|
||||
And I should see New Post button
|
||||
Then I should see Leave Team link
|
||||
When I click on Leave Team link
|
||||
Then user should be removed from team
|
||||
And I should see Join Team button
|
||||
And I should not see New Post button
|
||||
"""
|
||||
self._set_team_configuration_and_membership()
|
||||
self.team_page.visit()
|
||||
self.assertFalse(self.team_page.join_team_button_present)
|
||||
self.assert_team_details(num_members=1, invite_text=self.SEND_INVITE_TEXT)
|
||||
self.team_page.click_leave_team_link()
|
||||
self.assert_team_details(num_members=0, is_member=False)
|
||||
self.assertTrue(self.team_page.join_team_button_present)
|
||||
|
||||
@@ -1,23 +1,35 @@
|
||||
define([
|
||||
'underscore', 'common/js/spec_helpers/ajax_helpers', 'teams/js/models/team',
|
||||
'teams/js/views/team_join', 'teams/js/views/team_profile'
|
||||
], function (_, AjaxHelpers, TeamModel, TeamJoinView, TeamProfileView) {
|
||||
'teams/js/views/team_join'
|
||||
], function (_, AjaxHelpers, TeamModel, TeamJoinView) {
|
||||
'use strict';
|
||||
describe('TeamJoinView', function () {
|
||||
var createTeamsUrl,
|
||||
createTeamModelData,
|
||||
createMembershipData,
|
||||
createJoinView,
|
||||
verifyErrorMessage,
|
||||
ACCOUNTS_API_URL = '/api/user/v1/accounts/',
|
||||
TEAMS_URL = '/api/team/v0/teams/',
|
||||
TEAMS_MEMBERSHIP_URL = '/api/team/v0/team_membership/';
|
||||
|
||||
beforeEach(function () {
|
||||
setFixtures(
|
||||
'<div class="msg-content"><div class="copy"></div></div><div class="header-action-view"></div>'
|
||||
'<div class="teams-content"><div class="msg-content"><div class="copy"></div></div><div class="header-action-view"></div></div>'
|
||||
);
|
||||
});
|
||||
|
||||
verifyErrorMessage = function (requests, errorMessage, expectedMessage, joinTeam) {
|
||||
var view = createJoinView(1, 'ma', createTeamModelData('teamA', 'teamAlpha', []));
|
||||
if (joinTeam) {
|
||||
// if we want the error to return when user try to join team, respond with no membership
|
||||
AjaxHelpers.respondWithJson(requests, {"count": 0});
|
||||
view.$('.action.action-primary').click();
|
||||
}
|
||||
AjaxHelpers.respondWithTextError(requests, 400, errorMessage);
|
||||
expect($('.msg-content .copy').text().trim()).toBe(expectedMessage);
|
||||
};
|
||||
|
||||
createTeamsUrl = function (teamId) {
|
||||
return TEAMS_URL + teamId + '?expand=user';
|
||||
};
|
||||
@@ -148,27 +160,52 @@ define([
|
||||
expect(requests.length).toBe(0);
|
||||
});
|
||||
|
||||
it('shows correct error messages', function () {
|
||||
it('shows correct error message if user fails to join team', function () {
|
||||
var requests = AjaxHelpers.requests(this);
|
||||
|
||||
var verifyErrorMessage = function (requests, errorMessage, expectedMessage) {
|
||||
createJoinView(1, 'ma', createTeamModelData('teamA', 'teamAlpha', []));
|
||||
AjaxHelpers.respondWithTextError(requests, 400, errorMessage);
|
||||
expect($('.msg-content .copy').text().trim()).toBe(expectedMessage);
|
||||
};
|
||||
|
||||
// verify user_message
|
||||
verifyErrorMessage(
|
||||
requests,
|
||||
JSON.stringify({'user_message': 'Awesome! You got an error.'}),
|
||||
'Awesome! You got an error.'
|
||||
JSON.stringify({'user_message': "Can't be made member"}),
|
||||
"Can't be made member",
|
||||
true
|
||||
);
|
||||
|
||||
// verify generic error message
|
||||
verifyErrorMessage(
|
||||
requests,
|
||||
'',
|
||||
'An error occurred. Try again.'
|
||||
'An error occurred. Try again.',
|
||||
true
|
||||
);
|
||||
|
||||
// verify error message when json parsing succeeded but error message format is incorrect
|
||||
verifyErrorMessage(
|
||||
requests,
|
||||
JSON.stringify({'blah': "Can't be made member"}),
|
||||
'An error occurred. Try again.',
|
||||
true
|
||||
);
|
||||
});
|
||||
|
||||
it('shows correct error message if initializing the view fails', function () {
|
||||
// Rendering the view sometimes require fetching user's memberships. This may fail.
|
||||
var requests = AjaxHelpers.requests(this);
|
||||
|
||||
// verify user_message
|
||||
verifyErrorMessage(
|
||||
requests,
|
||||
JSON.stringify({'user_message': "Can't return user memberships"}),
|
||||
"Can't return user memberships",
|
||||
false
|
||||
);
|
||||
|
||||
// verify generic error message
|
||||
verifyErrorMessage(
|
||||
requests,
|
||||
'',
|
||||
'An error occurred. Try again.',
|
||||
false
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -5,27 +5,41 @@ define([
|
||||
], function (_, AjaxHelpers, TeamModel, TeamProfileView, TeamSpecHelpers, DiscussionSpecHelper) {
|
||||
'use strict';
|
||||
describe('TeamProfileView', function () {
|
||||
var profileView, createTeamProfileView;
|
||||
var profileView, createTeamProfileView, createTeamModelData, teamModel,
|
||||
DEFAULT_MEMBERSHIP = [
|
||||
{
|
||||
'user': {
|
||||
'username': 'bilbo',
|
||||
'profile_image': {
|
||||
'has_image': true,
|
||||
'image_url_medium': '/image-url'
|
||||
}
|
||||
}
|
||||
}
|
||||
];
|
||||
|
||||
beforeEach(function () {
|
||||
setFixtures('<div class="teams-content"><div class="msg-content"><div class="copy"></div></div></div>');
|
||||
DiscussionSpecHelper.setUnderscoreFixtures();
|
||||
});
|
||||
|
||||
createTeamModelData = function (options) {
|
||||
return {
|
||||
id: "test-team",
|
||||
name: "Test Team",
|
||||
discussion_topic_id: TeamSpecHelpers.testTeamDiscussionID,
|
||||
country: options.country || '',
|
||||
language: options.language || '',
|
||||
membership: options.membership || [],
|
||||
url: '/api/team/v0/teams/test-team'
|
||||
};
|
||||
};
|
||||
|
||||
createTeamProfileView = function(requests, options) {
|
||||
var model = new TeamModel(
|
||||
{
|
||||
id: "test-team",
|
||||
name: "Test Team",
|
||||
discussion_topic_id: TeamSpecHelpers.testTeamDiscussionID,
|
||||
country: options.country || '',
|
||||
language: options.language || '',
|
||||
membership: options.membership || []
|
||||
},
|
||||
{ parse: true }
|
||||
);
|
||||
teamModel = new TeamModel(createTeamModelData(options), { parse: true });
|
||||
profileView = new TeamProfileView({
|
||||
courseID: TeamSpecHelpers.testCourseID,
|
||||
model: model,
|
||||
model: teamModel,
|
||||
maxTeamSize: options.maxTeamSize || 3,
|
||||
requestUsername: 'bilbo',
|
||||
countries : [
|
||||
@@ -37,7 +51,8 @@ define([
|
||||
['', ''],
|
||||
['en', 'English'],
|
||||
['fr', 'French']
|
||||
]
|
||||
],
|
||||
teamMembershipDetailUrl: 'api/team/v0/team_membership/team_id,bilbo'
|
||||
});
|
||||
profileView.render();
|
||||
AjaxHelpers.expectRequest(
|
||||
@@ -62,16 +77,35 @@ define([
|
||||
view = createTeamProfileView(requests, {});
|
||||
expect(view.$('.discussion-thread').length).toEqual(3);
|
||||
});
|
||||
|
||||
it('shows New Post button when user joins a team', function () {
|
||||
var requests = AjaxHelpers.requests(this),
|
||||
view = createTeamProfileView(requests, {});
|
||||
|
||||
expect(view.$('.new-post-btn').length).toEqual(0);
|
||||
teamModel.set('membership', DEFAULT_MEMBERSHIP); // This should re-render the view.
|
||||
expect(view.$('.new-post-btn').length).toEqual(1);
|
||||
});
|
||||
|
||||
it('hides New Post button when user left a team', function () {
|
||||
var requests = AjaxHelpers.requests(this),
|
||||
view = createTeamProfileView(requests, {membership: DEFAULT_MEMBERSHIP});
|
||||
|
||||
expect(view.$('.new-post-btn').length).toEqual(1);
|
||||
teamModel.set('membership', []);
|
||||
expect(view.$('.new-post-btn').length).toEqual(0);
|
||||
});
|
||||
});
|
||||
|
||||
describe('TeamDetailsView', function() {
|
||||
|
||||
var assertTeamDetails = function(view, members) {
|
||||
var assertTeamDetails = function(view, members, memberOfTeam) {
|
||||
expect(view.$('.team-detail-header').text()).toBe('Team Details');
|
||||
expect(view.$('.team-country').text()).toContain('United States');
|
||||
expect(view.$('.team-language').text()).toContain('English');
|
||||
expect(view.$('.team-capacity').text()).toContain(members + ' / 3 Members');
|
||||
expect(view.$('.team-member').length).toBe(members);
|
||||
expect(Boolean(view.$('.leave-team-link').length)).toBe(memberOfTeam);
|
||||
};
|
||||
|
||||
describe('Non-Member', function() {
|
||||
@@ -82,7 +116,7 @@ define([
|
||||
country: 'US',
|
||||
language: 'en'
|
||||
});
|
||||
assertTeamDetails(view, 0);
|
||||
assertTeamDetails(view, 0, false);
|
||||
expect(view.$('.team-user-membership-status').length).toBe(0);
|
||||
|
||||
// Verify that invite and leave team sections are not present.
|
||||
@@ -105,17 +139,9 @@ define([
|
||||
var view = createTeamProfileView(requests, {
|
||||
country: 'US',
|
||||
language: 'en',
|
||||
membership: [{
|
||||
'user': {
|
||||
'username': 'bilbo',
|
||||
'profile_image': {
|
||||
'has_image': true,
|
||||
'image_url_medium': '/image-url'
|
||||
}
|
||||
}
|
||||
}]
|
||||
membership: DEFAULT_MEMBERSHIP
|
||||
});
|
||||
assertTeamDetails(view, 1);
|
||||
assertTeamDetails(view, 1, true);
|
||||
expect(view.$('.team-user-membership-status').text().trim()).toBe('You are a member of this team.');
|
||||
|
||||
// assert tooltip text.
|
||||
@@ -164,7 +190,7 @@ define([
|
||||
}]
|
||||
});
|
||||
|
||||
assertTeamDetails(view, 3);
|
||||
assertTeamDetails(view, 3, true);
|
||||
expect(view.$('.invite-header').text()).toContain('Invite Others');
|
||||
expect(view.$('.invite-text').text()).toContain('No invitations are available. This team is full.');
|
||||
expect(view.$('.invite-link-input').length).toBe(0);
|
||||
@@ -173,26 +199,71 @@ define([
|
||||
var requests = AjaxHelpers.requests(this);
|
||||
spyOn(TeamProfileView.prototype, 'selectText');
|
||||
|
||||
var view = createTeamProfileView(requests, {
|
||||
country: 'US',
|
||||
language: 'en',
|
||||
membership: [{
|
||||
'user': {
|
||||
'username': 'bilbo',
|
||||
'profile_image': {
|
||||
'has_image': true,
|
||||
'image_url_medium': '/image-url'
|
||||
}
|
||||
}
|
||||
}]
|
||||
});
|
||||
assertTeamDetails(view, 1);
|
||||
var view = createTeamProfileView(
|
||||
requests, {country: 'US', language: 'en', membership: DEFAULT_MEMBERSHIP}
|
||||
);
|
||||
assertTeamDetails(view, 1, true);
|
||||
|
||||
expect(view.$('.invite-link-input').length).toBe(1);
|
||||
|
||||
view.$('.invite-link-input').click();
|
||||
expect(view.selectText).toHaveBeenCalled();
|
||||
});
|
||||
it('can leave team successfully', function() {
|
||||
var requests = AjaxHelpers.requests(this);
|
||||
var leaveTeamLinkSelector = '.leave-team-link';
|
||||
|
||||
var view = createTeamProfileView(
|
||||
requests, { country: 'US', language: 'en', membership: DEFAULT_MEMBERSHIP}
|
||||
);
|
||||
assertTeamDetails(view, 1, true);
|
||||
|
||||
expect(view.$(leaveTeamLinkSelector).length).toBe(1);
|
||||
|
||||
// click on Leave Team link under Team Details
|
||||
view.$(leaveTeamLinkSelector).click();
|
||||
|
||||
// response to DELETE
|
||||
AjaxHelpers.respondWithNoContent(requests);
|
||||
|
||||
// response to model fetch request
|
||||
AjaxHelpers.respondWithJson(requests, createTeamModelData({country: 'US', language: 'en'}));
|
||||
|
||||
assertTeamDetails(view, 0, false);
|
||||
});
|
||||
it('shows correct error messages', function () {
|
||||
var requests = AjaxHelpers.requests(this);
|
||||
|
||||
var verifyErrorMessage = function (requests, errorMessage, expectedMessage) {
|
||||
var view = createTeamProfileView(
|
||||
requests, {country: 'US', language: 'en', membership: DEFAULT_MEMBERSHIP}
|
||||
);
|
||||
view.$('.leave-team-link').click();
|
||||
AjaxHelpers.respondWithTextError(requests, 400, errorMessage);
|
||||
expect($('.msg-content .copy').text().trim()).toBe(expectedMessage);
|
||||
};
|
||||
|
||||
// verify user_message
|
||||
verifyErrorMessage(
|
||||
requests,
|
||||
JSON.stringify({'user_message': "can't remove user from team"}),
|
||||
"can't remove user from team"
|
||||
);
|
||||
|
||||
// verify generic error message
|
||||
verifyErrorMessage(
|
||||
requests,
|
||||
'',
|
||||
'An error occurred. Try again.'
|
||||
);
|
||||
|
||||
// verify error message when json parsing succeeded but error message format is incorrect
|
||||
verifyErrorMessage(
|
||||
requests,
|
||||
JSON.stringify({'blah': "can't remove user from team"}),
|
||||
'An error occurred. Try again.'
|
||||
);
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -60,12 +60,7 @@ define(['backbone',
|
||||
}).done(function (data) {
|
||||
view.model.fetch({});
|
||||
}).fail(function (data) {
|
||||
try {
|
||||
var errors = JSON.parse(data.responseText);
|
||||
view.showMessage(errors.user_message);
|
||||
} catch (error) {
|
||||
view.showMessage(view.errorMessage);
|
||||
}
|
||||
TeamUtils.parseAndShowMessage(data, view.errorMessage);
|
||||
});
|
||||
},
|
||||
|
||||
@@ -97,12 +92,7 @@ define(['backbone',
|
||||
info.teamHasSpace = teamHasSpace;
|
||||
deferred.resolve(info);
|
||||
}).fail(function (data) {
|
||||
try {
|
||||
var errors = JSON.parse(data.responseText);
|
||||
view.showMessage(errors.user_message);
|
||||
} catch (error) {
|
||||
view.showMessage(view.errorMessage);
|
||||
}
|
||||
TeamUtils.parseAndShowMessage(data, view.errorMessage);
|
||||
deferred.reject();
|
||||
});
|
||||
} else {
|
||||
@@ -111,12 +101,6 @@ define(['backbone',
|
||||
}
|
||||
|
||||
return deferred.promise();
|
||||
},
|
||||
|
||||
showMessage: function (message) {
|
||||
$('.wrapper-msg').removeClass('is-hidden');
|
||||
$('.msg-content .copy').text(message);
|
||||
$('.wrapper-msg').focus();
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
@@ -6,21 +6,24 @@
|
||||
define(['backbone', 'underscore', 'gettext', 'teams/js/views/team_discussion',
|
||||
'teams/js/views/team_utils',
|
||||
'text!teams/templates/team-profile.underscore',
|
||||
'text!teams/templates/team-member.underscore'
|
||||
],
|
||||
'text!teams/templates/team-member.underscore'],
|
||||
function (Backbone, _, gettext, TeamDiscussionView, TeamUtils, teamTemplate, teamMemberTemplate) {
|
||||
var TeamProfileView = Backbone.View.extend({
|
||||
|
||||
errorMessage: gettext("An error occurred. Try again."),
|
||||
|
||||
events: {
|
||||
'click .invite-link-input': 'selectText'
|
||||
'click .invite-link-input': 'selectText',
|
||||
'click .leave-team-link': 'leaveTeam'
|
||||
},
|
||||
initialize: function (options) {
|
||||
this.listenTo(this.model, "change", this.render);
|
||||
this.courseID = options.courseID;
|
||||
this.maxTeamSize = options.maxTeamSize;
|
||||
this.readOnly = options.readOnly;
|
||||
this.requestUsername = options.requestUsername;
|
||||
this.isPrivileged = options.isPrivileged;
|
||||
this.teamInviteUrl = options.teamInviteUrl;
|
||||
this.teamMembershipDetailUrl = options.teamMembershipDetailUrl;
|
||||
|
||||
this.countries = TeamUtils.selectorOptionsArrayToHashWithBlank(options.countries);
|
||||
this.languages = TeamUtils.selectorOptionsArrayToHashWithBlank(options.languages);
|
||||
@@ -28,16 +31,18 @@
|
||||
},
|
||||
|
||||
render: function () {
|
||||
var memberships = this.model.get('membership');
|
||||
var discussionTopicID = this.model.get('discussion_topic_id');
|
||||
var memberships = this.model.get('membership'),
|
||||
discussionTopicID = this.model.get('discussion_topic_id'),
|
||||
isMember = TeamUtils.isUserMemberOfTeam(memberships, this.requestUsername);
|
||||
|
||||
this.$el.html(_.template(teamTemplate, {
|
||||
courseID: this.courseID,
|
||||
discussionTopicID: discussionTopicID,
|
||||
readOnly: this.readOnly,
|
||||
readOnly: !(this.isPrivileged || isMember),
|
||||
country: this.countries[this.model.get('country')],
|
||||
language: this.languages[this.model.get('language')],
|
||||
membershipText: TeamUtils.teamCapacityText(memberships.length, this.maxTeamSize),
|
||||
isMember: TeamUtils.isUserMemberOfTeam(memberships, this.requestUsername),
|
||||
isMember: isMember,
|
||||
hasCapacity: memberships.length < this.maxTeamSize,
|
||||
inviteLink: this.teamInviteUrl
|
||||
|
||||
@@ -65,6 +70,19 @@
|
||||
selectText: function(event) {
|
||||
event.preventDefault();
|
||||
$(event.currentTarget).select();
|
||||
},
|
||||
|
||||
leaveTeam: function (event) {
|
||||
event.preventDefault();
|
||||
var view = this;
|
||||
$.ajax({
|
||||
type: 'DELETE',
|
||||
url: view.teamMembershipDetailUrl.replace('team_id', view.model.get('id'))
|
||||
}).done(function (data) {
|
||||
view.model.fetch({});
|
||||
}).fail(function (data) {
|
||||
TeamUtils.parseAndShowMessage(data, view.errorMessage);
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
@@ -28,8 +28,9 @@
|
||||
maxMemberCount
|
||||
),
|
||||
{memberCount: memberCount, maxMemberCount: maxMemberCount}, true
|
||||
)
|
||||
);
|
||||
},
|
||||
|
||||
isUserMemberOfTeam: function(memberships, requestUsername) {
|
||||
return _.isObject(
|
||||
_.find(memberships, function(membership)
|
||||
@@ -37,8 +38,27 @@
|
||||
return membership.user.username === requestUsername;
|
||||
})
|
||||
);
|
||||
},
|
||||
|
||||
showMessage: function (message) {
|
||||
var messageElement = $('.teams-content .wrapper-msg');
|
||||
messageElement.removeClass('is-hidden');
|
||||
$('.teams-content .msg-content .copy').text(message);
|
||||
messageElement.focus();
|
||||
},
|
||||
|
||||
/**
|
||||
* Parse `data` and show user message. If parsing fails than show `genericErrorMessage`
|
||||
*/
|
||||
parseAndShowMessage: function (data, genericErrorMessage) {
|
||||
try {
|
||||
var errors = JSON.parse(data.responseText);
|
||||
this.showMessage(_.isUndefined(errors.user_message) ? genericErrorMessage : errors.user_message);
|
||||
} catch (error) {
|
||||
this.showMessage(genericErrorMessage);
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
});
|
||||
|
||||
}).call(this, define || RequireJS.define);
|
||||
|
||||
@@ -53,6 +53,7 @@
|
||||
this.topicUrl = options.topicUrl;
|
||||
this.teamsUrl = options.teamsUrl;
|
||||
this.teamMembershipsUrl = options.teamMembershipsUrl;
|
||||
this.teamMembershipDetailUrl = options.teamMembershipDetailUrl;
|
||||
this.maxTeamSize = options.maxTeamSize;
|
||||
this.languages = options.languages;
|
||||
this.countries = options.countries;
|
||||
@@ -276,16 +277,16 @@
|
||||
courseID = this.courseID;
|
||||
self.getTopic(topicID).done(function(topic) {
|
||||
self.getTeam(teamID, true).done(function(team) {
|
||||
var readOnly = self.readOnlyDiscussion(team),
|
||||
view = new TeamProfileView({
|
||||
var view = new TeamProfileView({
|
||||
courseID: courseID,
|
||||
model: team,
|
||||
readOnly: readOnly,
|
||||
maxTeamSize: self.maxTeamSize,
|
||||
isPrivileged: self.userInfo.privileged,
|
||||
requestUsername: self.userInfo.username,
|
||||
countries: self.countries,
|
||||
languages: self.languages,
|
||||
teamInviteUrl: self.teamsBaseUrl + '#teams/' + topicID + '/' + teamID + '?invite=true'
|
||||
teamInviteUrl: self.teamsBaseUrl + '#teams/' + topicID + '/' + teamID + '?invite=true',
|
||||
teamMembershipDetailUrl: self.teamMembershipDetailUrl
|
||||
});
|
||||
var teamJoinView = new TeamJoinView(
|
||||
{
|
||||
@@ -389,11 +390,11 @@
|
||||
var team = this.teamsCollection ? this.teamsCollection.get(teamID) : null,
|
||||
self = this,
|
||||
deferred = $.Deferred(),
|
||||
teamUrl;
|
||||
teamUrl = this.teamsUrl + teamID + (expandUser ? '?expand=user': '');
|
||||
if (team) {
|
||||
team.url = teamUrl;
|
||||
deferred.resolve(team);
|
||||
} else {
|
||||
teamUrl = this.teamsUrl + teamID + (expandUser ? '?expand=user': '');
|
||||
team = new TeamModel({
|
||||
id: teamID,
|
||||
url: teamUrl
|
||||
|
||||
@@ -40,6 +40,7 @@
|
||||
topicsUrl: '${ topics_url }',
|
||||
teamsUrl: '${ teams_url }',
|
||||
teamMembershipsUrl: '${ team_memberships_url }',
|
||||
teamMembershipDetailUrl: '${ team_membership_detail_url }',
|
||||
maxTeamSize: ${ course.teams_max_size },
|
||||
languages: ${ json.dumps(languages, cls=EscapedEdxJSONEncoder) },
|
||||
countries: ${ json.dumps(countries, cls=EscapedEdxJSONEncoder) },
|
||||
|
||||
@@ -108,6 +108,7 @@ class TeamsDashboardView(View):
|
||||
"topics_url": reverse('topics_list', request=request),
|
||||
"teams_url": reverse('teams_list', request=request),
|
||||
"team_memberships_url": reverse('team_membership_list', request=request),
|
||||
"team_membership_detail_url": reverse('team_membership_detail', args=['team_id', user.username]),
|
||||
"languages": settings.ALL_LANGUAGES,
|
||||
"countries": list(countries),
|
||||
"disable_courseware_js": True,
|
||||
|
||||
Reference in New Issue
Block a user