Newer
Older
const { findLast, isEmpty, maxBy, get, flatMap } = require('lodash')
Andrei Cioromila
committed
const Fragment = require('./Fragment')

Mihail Hagiu
committed
class Collection {
constructor({ collection = {} }) {
this.collection = collection
}
async updateStatusByRecommendation({
recommendation,
isHandlingEditor = false,
}) {
let newStatus
if (isHandlingEditor) {
newStatus = 'pendingApproval'
if (['minor', 'major'].includes(recommendation)) {
newStatus = 'revisionRequested'
}
} else {
if (recommendation === 'minor') {
newStatus = 'reviewCompleted'
}
if (recommendation === 'major') {
}
}
this.updateStatus({ newStatus })
}
async updateFinalStatusByRecommendation({ recommendation }) {
let newStatus
switch (recommendation) {
case 'reject':
newStatus = 'rejected'
break
case 'publish':
newStatus = 'accepted'
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
break
case 'return-to-handling-editor':
newStatus = 'reviewCompleted'
break
default:
break
}
await this.updateStatus({ newStatus })
}
async updateStatus({ newStatus }) {
this.collection.status = newStatus
await this.collection.save()
}
async addHandlingEditor({ user, invitation }) {
this.collection.handlingEditor = {
id: user.id,
name: `${user.firstName} ${user.lastName}`,
invitedOn: invitation.invitedOn,
respondedOn: invitation.respondedOn,
email: user.email,
hasAnswer: invitation.hasAnswer,
isAccepted: invitation.isAccepted,
}
await this.updateStatus({ newStatus: 'heInvited' })
}
async updateHandlingEditor({ isAccepted }) {
const { collection: { handlingEditor } } = this
handlingEditor.hasAnswer = true
handlingEditor.isAccepted = isAccepted
handlingEditor.respondedOn = Date.now()
const newStatus = isAccepted ? 'heAssigned' : 'submitted'
await this.updateStatus({ newStatus })
async updateStatusByNumberOfReviewers({ invitations }) {
const reviewerInvitations = invitations.filter(
inv => inv.role === 'reviewer',
)
if (reviewerInvitations.length === 0)
await this.updateStatus({ newStatus: 'heAssigned' })
}
async updateStatusOnRecommendation({ isEditorInChief, recommendation }) {
if (isEditorInChief) {
if (recommendation === 'return-to-handling-editor') {
this.updateStatus({ newStatus: 'reviewCompleted' })
} else {
this.updateFinalStatusByRecommendation({
recommendation,
})
}
} else {
this.updateStatusByRecommendation({
recommendation,
isHandlingEditor: true,
})
}
}
Sebastian Mihalache
committed
getHELastName() {
Sebastian Mihalache
committed
const [firstName, lastName] = this.collection.handlingEditor.name.split(' ')
return lastName || firstName
Sebastian Mihalache
committed
}

Mihail Hagiu
committed
async getAllCollectionFragments({ FragmentModel }) {
const allCollectionFragments = await Promise.all(
get(this.collection, 'fragments', []).map(async fragmentId => {

Mihail Hagiu
committed
const fragment = await FragmentModel.find(fragmentId)
return fragment
}),
)
return allCollectionFragments
}

Mihail Hagiu
committed
async getReviewerNumber({ userId, FragmentModel }) {

Mihail Hagiu
committed
const allCollectionFragments = await this.getAllCollectionFragments({
FragmentModel,
})
const allCollectionInvitations = flatMap(
allCollectionFragments,
fragment => fragment.invitations,

Mihail Hagiu
committed
)
const allNumberedInvitationsForUser = allCollectionInvitations

Mihail Hagiu
committed
.filter(invite => invite.userId === userId)

Mihail Hagiu
committed
.filter(invite => invite.reviewerNumber)
if (isEmpty(allNumberedInvitationsForUser)) {
const maxReviewerNumber = get(
maxBy(allCollectionInvitations, 'reviewerNumber'),
'reviewerNumber',
0,
)
return maxReviewerNumber + 1
}

Mihail Hagiu
committed
return allNumberedInvitationsForUser[0].reviewerNumber
}
Andrei Cioromila
committed
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
// eslint-disable-next-line class-methods-use-this
hasAtLeastOneReviewReport(fragments) {
return fragments.some(fragment =>
new Fragment({ fragment }).hasReviewReport(),
)
}
canHEMakeRecommendation(fragments, fragmentHelper) {
if (this.collection.fragments.length === 1) {
return fragmentHelper.hasReviewReport()
}
const previousVersionRecommendations = get(
fragments[fragments.length - 2],
'recommendations',
[],
)
const lastRecommendationByHE = findLast(
previousVersionRecommendations,
recommendation =>
recommendation.userId === this.collection.handlingEditor.id &&
recommendation.recommendationType === 'editorRecommendation',
)
if (lastRecommendationByHE.recommendation === 'minor') {
return this.hasAtLeastOneReviewReport(fragments)
} else if (lastRecommendationByHE.recommendation === 'major') {
return fragmentHelper.hasReviewReport()
}
}
}
module.exports = Collection