Assignee field. In Progress.

Thanks to xet7 !

Related #2452
This commit is contained in:
Lauri Ojansivu 2019-08-13 02:33:41 +03:00
parent 411ded513d
commit 306301e881
2 changed files with 164 additions and 1 deletions

View file

@ -451,10 +451,11 @@ Filter = {
// before changing the schema.
labelIds: new SetFilter(),
members: new SetFilter(),
assignees: new SetFilter(),
customFields: new SetFilter('_id'),
advanced: new AdvancedFilter(),
_fields: ['labelIds', 'members', 'customFields'],
_fields: ['labelIds', 'members', 'assignees', 'customFields'],
// We don't filter cards that have been added after the last filter change. To
// implement this we keep the id of these cards in this `_exceptions` fields

View file

@ -201,6 +201,14 @@ Cards.attachSchema(
optional: true,
defaultValue: [],
},
assignees: {
/**
* list of assignees (user IDs) who are responsible for completing card
*/
type: [String],
optional: true,
defaultValue: [],
},
receivedAt: {
/**
* Date the card was received
@ -409,6 +417,10 @@ Cards.helpers({
return _.contains(this.getMembers(), memberId);
},
isAssignee(assigneeId) {
return _.contains(this.getAssignee(), assigneeId);
},
activities() {
if (this.isLinkedCard()) {
return Activities.find(
@ -743,6 +755,20 @@ Cards.helpers({
}
},
getAssignees() {
if (this.isLinkedCard()) {
const card = Cards.findOne({ _id: this.linkedId });
return card.assignees;
} else if (this.isLinkedBoard()) {
const board = Boards.findOne({ _id: this.linkedId });
return board.activeAssignees().map(assignee => {
return assignee.userId;
});
} else {
return this.assignees;
}
},
assignMember(memberId) {
if (this.isLinkedCard()) {
return Cards.update(
@ -760,6 +786,23 @@ Cards.helpers({
}
},
assignAssignee(assigneeId) {
if (this.isLinkedCard()) {
return Cards.update(
{ _id: this.linkedId },
{ $addToSet: { assignees: assigneeId } },
);
} else if (this.isLinkedBoard()) {
const board = Boards.findOne({ _id: this.linkedId });
return board.addAssignee(assigneeId);
} else {
return Cards.update(
{ _id: this._id },
{ $addToSet: { assignees: assigneeId } },
);
}
},
unassignMember(memberId) {
if (this.isLinkedCard()) {
return Cards.update(
@ -774,6 +817,23 @@ Cards.helpers({
}
},
unassignAssignee(assigneeId) {
if (this.isLinkedCard()) {
return Cards.update(
{ _id: this.linkedId },
{ $pull: { assignees: assigneeId } },
);
} else if (this.isLinkedBoard()) {
const board = Boards.findOne({ _id: this.linkedId });
return board.removeAssignee(assigneeId);
} else {
return Cards.update(
{ _id: this._id },
{ $pull: { assignees: assigneeId } },
);
}
},
toggleMember(memberId) {
if (this.getMembers() && this.getMembers().indexOf(memberId) > -1) {
return this.unassignMember(memberId);
@ -782,6 +842,14 @@ Cards.helpers({
}
},
toggleAssignee(assigneeId) {
if (this.getAssignees() && this.getAssignees().indexOf(assigneeId) > -1) {
return this.unassignAssignee(assigneeId);
} else {
return this.assignAssignee(assigneeId);
}
},
getReceived() {
if (this.isLinkedCard()) {
const card = Cards.findOne({ _id: this.linkedId });
@ -1124,6 +1192,14 @@ Cards.mutations({
};
},
assignAssignee(assigneeId) {
return {
$addToSet: {
assignees: assigneeId,
},
};
},
unassignMember(memberId) {
return {
$pull: {
@ -1132,6 +1208,14 @@ Cards.mutations({
};
},
unassignAssignee(assigneeId) {
return {
$pull: {
assignee: assigneeId,
},
};
},
toggleMember(memberId) {
if (this.members && this.members.indexOf(memberId) > -1) {
return this.unassignMember(memberId);
@ -1140,6 +1224,14 @@ Cards.mutations({
}
},
toggleAssignee(assigneeId) {
if (this.assignees && this.assignees.indexOf(assigneeId) > -1) {
return this.unassignAssignee(assigneeId);
} else {
return this.assignAssignee(assigneeId);
}
},
assignCustomField(customFieldId) {
return {
$addToSet: {
@ -1414,6 +1506,28 @@ function cardMembers(userId, doc, fieldNames, modifier) {
}
}
function cardAssignees(userId, doc, fieldNames, modifier) {
if (!_.contains(fieldNames, 'assignees')) return;
let assigneeId;
// Say hello to the new assignee
if (modifier.$addToSet && modifier.$addToSet.assignees) {
assigneeId = modifier.$addToSet.assignees;
const username = Users.findOne(assigneeId).username;
if (!_.contains(doc.assignees, assigneeId)) {
Activities.insert({
userId,
username,
activityType: 'joinAssignee',
boardId: doc.boardId,
cardId: doc._id,
assigneeId,
listId: doc.listId,
swimlaneId: doc.swimlaneId,
});
}
}
}
// Say goodbye to the former member
if (modifier.$pull && modifier.$pull.members) {
memberId = modifier.$pull.members;
@ -1432,6 +1546,25 @@ function cardMembers(userId, doc, fieldNames, modifier) {
});
}
}
// Say goodbye to the former assignee
if (modifier.$pull && modifier.$pull.assignees) {
assigneeId = modifier.$pull.assignees;
const username = Users.findOne(assigneeId).username;
// Check that the former assignee is assignee of the card
if (_.contains(doc.assignees, assigneeId)) {
Activities.insert({
userId,
username,
activityType: 'unjoinAssignee',
boardId: doc.boardId,
cardId: doc._id,
assigneeId,
listId: doc.listId,
swimlaneId: doc.swimlaneId,
});
}
}
}
function cardLabels(userId, doc, fieldNames, modifier) {
@ -1650,6 +1783,12 @@ if (Meteor.isServer) {
updateActivities(doc, fieldNames, modifier);
});
// Add a new activity if we add or remove a assignee to the card
Cards.before.update((userId, doc, fieldNames, modifier) => {
cardAssignees(userId, doc, fieldNames, modifier);
updateActivities(doc, fieldNames, modifier);
});
// Add a new activity if we add or remove a label to the card
Cards.before.update((userId, doc, fieldNames, modifier) => {
cardLabels(userId, doc, fieldNames, modifier);
@ -1809,6 +1948,7 @@ if (Meteor.isServer) {
* @param {string} description the description of the new card
* @param {string} swimlaneId the swimlane ID of the new card
* @param {string} [members] the member IDs list of the new card
* @param {string} [assignees] the assignee IDs list of the new card
* @return_type {_id: string}
*/
JsonRoutes.add('POST', '/api/boards/:boardId/lists/:listId/cards', function(
@ -1830,6 +1970,7 @@ if (Meteor.isServer) {
_id: req.body.authorId,
});
const members = req.body.members || [req.body.authorId];
const assignees = req.body.assignees;
if (typeof check !== 'undefined') {
const id = Cards.direct.insert({
title: req.body.title,
@ -1841,6 +1982,7 @@ if (Meteor.isServer) {
swimlaneId: req.body.swimlaneId,
sort: currentCards.count(),
members,
assignees,
});
JsonRoutes.sendResult(res, {
code: 200,
@ -1892,6 +2034,7 @@ if (Meteor.isServer) {
* @param {string} [labelIds] the new list of label IDs attached to the card
* @param {string} [swimlaneId] the new swimlane ID of the card
* @param {string} [members] the new list of member IDs attached to the card
* @param {string} [assignees] the new list of assignee IDs attached to the card
* @param {string} [requestedBy] the new requestedBy field of the card
* @param {string} [assignedBy] the new assignedBy field of the card
* @param {string} [receivedAt] the new receivedAt field of the card
@ -2152,6 +2295,25 @@ if (Meteor.isServer) {
{ $set: { members: newmembers } },
);
}
if (req.body.hasOwnProperty('assignees')) {
let newassignees = req.body.assignees;
if (_.isString(newassignees)) {
if (newassignees === '') {
newassignees = null;
} else {
newassignees = [newassignees];
}
}
Cards.direct.update(
{
_id: paramCardId,
listId: paramListId,
boardId: paramBoardId,
archived: false,
},
{ $set: { assignees: newassignees } },
);
}
if (req.body.hasOwnProperty('swimlaneId')) {
const newParamSwimlaneId = req.body.swimlaneId;
Cards.direct.update(