diff --git a/test/api/v3/integration/groups/POST-groups_invite.test.js b/test/api/v3/integration/groups/POST-groups_invite.test.js
index f677f038fe..157cf01294 100644
--- a/test/api/v3/integration/groups/POST-groups_invite.test.js
+++ b/test/api/v3/integration/groups/POST-groups_invite.test.js
@@ -7,7 +7,7 @@ import {
} from '../../../../helpers/api-integration/v3';
const INVITES_LIMIT = 100;
-const PARTY_LIMIT_MEMBERS = 30;
+const PARTY_LIMIT_MEMBERS = 29;
const MAX_EMAIL_INVITES_BY_USER = 200;
describe('Post /groups/:groupId/invite', () => {
@@ -650,7 +650,7 @@ describe('Post /groups/:groupId/invite', () => {
.to.eventually.be.rejected.and.eql({
code: 400,
error: 'BadRequest',
- message: t('partyExceedsMembersLimit', { maxMembersParty: PARTY_LIMIT_MEMBERS }),
+ message: t('partyExceedsMembersLimit', { maxMembersParty: PARTY_LIMIT_MEMBERS + 1 }),
});
}).timeout(10000);
});
diff --git a/website/client/src/components/header/index.vue b/website/client/src/components/header/index.vue
index bbe5842a7d..202c5f0e45 100644
--- a/website/client/src/components/header/index.vue
+++ b/website/client/src/components/header/index.vue
@@ -145,6 +145,9 @@ export default {
currentWidth: 0,
inviteModalGroup: undefined,
inviteModalGroupType: undefined,
+ group: {},
+ members: [],
+ membersLoaded: false,
};
},
computed: {
@@ -236,14 +239,26 @@ export default {
this.$root.$emit('bv::show::modal', 'create-party-modal');
}
},
- async showPartyMembers () {
- const party = await this.$store.dispatch('party:getParty');
+ loadMembers (payload = null) {
+ // Remove unnecessary data
+ if (payload && payload.challengeId) {
+ delete payload.challengeId;
+ }
+ return this.$store.dispatch('members:getGroupMembers', payload);
+ },
+ async showPartyMembers () {
+ this.group = await this.$store.dispatch('party:getParty');
+ this.group = this.$store.state.party.data;
+ this.membersLoaded = true;
+ this.members = this.partyMembers;
+ this.$store.state.memberModalOptions.loading = false;
this.$root.$emit('habitica:show-member-modal', {
- groupId: party.data._id,
- viewingMembers: this.partyMembers,
- group: party.data,
- fetchMoreMembers: p => this.$store.dispatch('members:getGroupMembers', p),
+ groupId: this.group._id,
+ group: this.group,
+ memberCount: this.group.memberCount,
+ viewingMembers: this.members,
+ fetchMoreMembers: this.loadMembers,
});
},
setPartyMembersWidth ($event) {
diff --git a/website/client/src/components/selectMembersModal.vue b/website/client/src/components/selectMembersModal.vue
index 9326f09c7d..ef9d9eeb1d 100644
--- a/website/client/src/components/selectMembersModal.vue
+++ b/website/client/src/components/selectMembersModal.vue
@@ -74,6 +74,19 @@
v-if="members.length > 3"
class="row gradient"
>
+
+
+
+
+
@@ -157,11 +170,13 @@ export default {
components: {
MemberDetails,
},
- props: ['group', 'hideBadge', 'item'],
+ props: ['hideBadge', 'item'],
data () {
return {
sortOption: '',
members: [],
+ group: {},
+ invites: [],
memberToRemove: '',
sortOptions: [
{
@@ -210,6 +225,14 @@ export default {
return this.members;
},
+ isLoadMoreAvailable () {
+ // Only available if the current length of `members` is less than the
+ // total size of the Group/Challenge
+ return this.members.length < this.$store.state.memberModalOptions.memberCount;
+ },
+ challengeId () {
+ return this.$store.state.memberModalOptions.challengeId;
+ },
groupId () {
return this.$store.state.groupId || this.group._id;
},
@@ -222,7 +245,20 @@ export default {
},
},
methods: {
+ loadMembers (payload = null) {
+ // Remove unnecessary data
+ if (payload && payload.challengeId) {
+ delete payload.challengeId;
+ }
+
+ return this.$store.dispatch('members:getGroupMembers', payload);
+ },
async getMembers () {
+ this.group = await this.$store.dispatch('party:getParty');
+ this.group = this.$store.state.party.data;
+ this.$store.state.memberModalOptions.memberCount = this.group.memberCount;
+ this.$store.state.memberModalOptions.fetchMoreMembers = this.loadMembers;
+
const { groupId } = this;
if (groupId && groupId !== 'challenge') {
const members = await this.$store.dispatch('members:getGroupMembers', {
@@ -230,6 +266,11 @@ export default {
includeAllPublicFields: true,
});
this.members = members;
+ const invites = await this.$store.dispatch('members:getGroupInvites', {
+ groupId,
+ includeAllPublicFields: true,
+ });
+ this.invites = invites;
}
if ((!this.members || this.members.length === 0)
@@ -241,6 +282,20 @@ export default {
if (!this.members || (this.members.length === 0 && !this.groupId)) {
this.members = [this.user];
}
+ this.$store.state.memberModalOptions.viewingMembers = this.members;
+ },
+ async loadMoreMembers () {
+ const lastMember = this.members[this.members.length - 1];
+ if (!lastMember) return;
+
+ const newMembers = await this.$store.state.memberModalOptions.fetchMoreMembers({
+ challengeId: this.challengeId,
+ groupId: this.groupId,
+ lastMemberId: lastMember._id,
+ includeAllPublicFields: true,
+ });
+
+ this.members = this.members.concat(newMembers);
},
close () {
this.$root.$emit('bv::hide::modal', 'select-member-modal');
diff --git a/website/common/script/constants.js b/website/common/script/constants.js
index 27ec659adc..f2eb56a4c0 100644
--- a/website/common/script/constants.js
+++ b/website/common/script/constants.js
@@ -28,7 +28,7 @@ export const SUPPORTED_SOCIAL_NETWORKS = [
export const GUILDS_PER_PAGE = 30; // number of guilds to return per page when using pagination
-export const PARTY_LIMIT_MEMBERS = 30;
+export const PARTY_LIMIT_MEMBERS = 29;
export const MINIMUM_PASSWORD_LENGTH = 8;
diff --git a/website/server/models/group.js b/website/server/models/group.js
index 38b913c139..e8d98627fe 100644
--- a/website/server/models/group.js
+++ b/website/server/models/group.js
@@ -491,7 +491,7 @@ schema.statics.validateInvitations = async function getInvitationErr (invites, r
memberCount += totalInvites;
if (memberCount > shared.constants.PARTY_LIMIT_MEMBERS) {
- throw new BadRequest(res.t('partyExceedsMembersLimit', { maxMembersParty: shared.constants.PARTY_LIMIT_MEMBERS }));
+ throw new BadRequest(res.t('partyExceedsMembersLimit', { maxMembersParty: shared.constants.PARTY_LIMIT_MEMBERS + 1 }));
}
}
};