1const Apify = require('apify');
2const mailgun = require('mailgun-js');
3const request = require('request-promise');
4const typeCheck = require('type-check').typeCheck;
5const sleep = require('sleep');
6const _ = require('underscore');
7const util = require('util');
8
9// Input data attributes types
10const INPUT_TYPES = `{
11 to: String,
12 subject: String,
13 text: String,
14 isMock: Maybe Boolean,
15 cc: Maybe String,
16 bcc: Maybe String,
17 actId: Maybe String,
18 _id: Maybe String,
19 attachments: Maybe [{filename: String, data: String}],
20 }`;
21// Allowed mail attributes
22const MAIL_ATTRIBUTES = ['to', 'subject', 'text', 'cc', 'bcc'];
23
24Apify.main(async () => {
25 // Gets input of your act
26 let input = await Apify.getValue('INPUT');
27 if (!input) {
28 throw new Error('Input is missing!');
29 }
30 // Data from crawler finish webhook was in input.data JSON string
31 if (input.data) {
32 input = Object.assign(input, JSON.parse(input.data));
33 delete input.data;
34 }
35 // Checks input
36 if (!typeCheck(INPUT_TYPES, input)) {
37 console.log(`Invalid input:\n${JSON.stringify(input)}\nData types:\n${INPUT_TYPES}\nAct failed!`);
38 throw new Error('Invalid input data');
39 }
40
41 // Sends mail
42 const mail = _.pick(input, MAIL_ATTRIBUTES);
43 mail.from = 'Apifier Mailer <postmaster@apify-mailer.com>';
44 const sender = mailgun({
45 apiKey: process.env.MAILGUN_API_KEY,
46 domain: process.env.MAILGUN_DOMAIN
47 });
48
49 // Gets all attachments
50 if (input.attachments) {
51 mail.attachment = [];
52 for (let attachment of input.attachments) {
53 const attch = new sender.Attachment({
54 data: Buffer.from(attachment.data, 'base64'),
55 filename: attachment.filename
56 });
57 mail.attachment.push(attch);
58 }
59 }
60
61 console.log(mail);
62 if (input.isMock) {
63 console.log(`Mail:\n${JSON.stringify(mail)}`)
64 } else {
65 const senderBody = await sender.messages().send(mail);
66 console.log(`Email with id ${senderBody.id} was send to ${mail.to}.`);
67 }
68 // Sleeps act for 10s
69 // NOTE: We use sleep to avoid instant usage
70 sleep.sleep(10);
71});