Skip to content
Snippets Groups Projects
Code owners
Assign users and groups as approvers for specific file changes. Learn more.
invitations.js 3.54 KiB
const config = require('config')
const { get } = require('lodash')
const Email = require('@pubsweet/component-email-templating')

const unsubscribeSlug = config.get('unsubscribe.url')
const inviteReviewerPath = config.get('invite-reviewer.url')
const { staffEmail, name: journalName } = config.get('journal')

const { services, Fragment } = require('pubsweet-component-helper-service')

const { getEmailCopy } = require('./emailCopy')

module.exports = {
  async sendInvitations({
    resend,
    baseUrl,
    fragment,
    UserModel,
    timestamp,
    collection,
    invitation,
    invitedUser,
  }) {
    const fragmentHelper = new Fragment({ fragment })
    const { title, abstract } = await fragmentHelper.getFragmentData({
      handlingEditor: collection.handlingEditor,
    })
    const {
      activeAuthors: authors,
      submittingAuthor,
    } = await fragmentHelper.getAuthorData({
      UserModel,
    })

    const subjectBaseText = `${collection.customId}: Review`

    let queryParams = {
      invitationId: invitation.id,
      agree: true,
    }

    const detailsPath = `/projects/${collection.id}/versions/${
      fragment.id
    }/details`

    const declineLink = services.createUrl(baseUrl, inviteReviewerPath, {
      ...queryParams,
      agree: false,
      fragmentId: fragment.id,
      collectionId: collection.id,
      invitationToken: invitedUser.accessTokens.invitation,
    })

    let agreeLink = services.createUrl(baseUrl, detailsPath, queryParams)

    if (!invitedUser.isConfirmed) {
      queryParams = {
        ...queryParams,
        agree: true,
        fragmentId: fragment.id,
        email: invitedUser.email,
        collectionId: collection.id,
        token: invitedUser.accessTokens.passwordReset,
      }
      agreeLink = services.createUrl(baseUrl, inviteReviewerPath, queryParams)
    }

    const authorsList = authors.map(
      author => `${author.firstName} ${author.lastName}`,
    )

    const handlingEditor = get(collection, 'handlingEditor', {})
    const email = new Email({
      type: 'user',
      fromEmail: `${handlingEditor.name} <${staffEmail}>`,
      toUser: {
        email: invitedUser.email,
        name: `${invitedUser.lastName}`,
      },
      content: {
        title,
        abstract,
        agreeLink,
        declineLink,
        signatureJournal: journalName,
        signatureName: handlingEditor.name,
        authorsList: authorsList.join(', '),
        subject: `${subjectBaseText} invitation`,
        detailsLink: services.createUrl(baseUrl, detailsPath),
        unsubscribeLink: services.createUrl(baseUrl, unsubscribeSlug, {
          id: invitedUser.id,
          token: invitedUser.accessTokens.unsubscribe,
        }),
      },
    })

    sendInvitedUserEmail({
      email,
      title,
      resend,
      timestamp,
      authorName: `${submittingAuthor.firstName} ${submittingAuthor.lastName}`,
    })
  },
}

const sendInvitedUserEmail = async ({
  email,
  resend,
  title,
  authorName,
  timestamp,
}) => {
  let daysExpected = 14
  let emailType = 'reviewer-invitation'
  let titleText = `A manuscript titled "${title}" by ${authorName} et al.`

  if (resend) {
    emailType = 'reviewer-resend-invitation'
    daysExpected = 0
    email.content.subject = `${email.content.subject} reminder`
    titleText = `the manuscript titled "${title}" by ${authorName}`
  }

  const { html, text } = email.getInvitationBody({
    emailBodyProps: getEmailCopy({
      emailType,
      titleText,
      expectedDate: services.getExpectedDate({ timestamp, daysExpected }),
    }),
  })

  email.sendEmail({ html, text })
}