一、前言

上一节我们演示了如何用Node的各种包去抓取电影天堂最新电影列表,接下来我们会讲解如何发送我们已抓取的数据到我们的QQ邮箱。如果你还没看到之前是如何抓取数据,请点击 Node.js 抓取电影天堂新上电影节目单及ftp链接。

二、效果图

最终效果:

三、代码实现

1. 首先安装依赖包:

```bash

npm i utility nodemailer --save-dev

```

2. 创建一个名为 sendEmail.js 的文件,编写以下代码:

```javascript

// 引入依赖包

const nodemailer = require('nodemailer');

const fs = require('fs');

// 设置邮件发送者和接收者

const from = '****@qq.com';

const to = '***@qq.com';

// 设置邮件主题和内容

const subject = '电影天堂新上电影';

const htmlContent = '

这里是邮件正文内容

';

// 设置附件路径和文件名

const attachments = [

{ filename: '迅雷极速版.exe', path: './lib/ThunderSpeed.exe' },

{ filename: 'ftp.txt', path: './doc/dy.txt' },

{ filename: 'dytt.html', content: '' },

{ filename: 'alipay.jpg', path: './doc/wz.jpg' },

];

// 将附件内容读入内存并添加到邮件内容中

attachments.forEach((attachment) => {

const fileStream = fs.createReadStream(attachment.path);

htmlContent += `

${attachment.filename}

`; // 在邮件内容中添加附件下载链接

});

// 创建邮件选项对象

const mailOptions = {

from: from,

to: to,

subject: subject,

html: htmlContent,

attachments: attachments,

};

// 创建邮件传输器对象并发送邮件

const transporter = nodemailer.createTransport({ /* 这里填写你的邮箱配置 */ });

transporter.sendMail(mailOptions, (error, info) => {

if (error) {

console.log('邮件发送失败:', error);

} else {

console.log('邮件发送成功:', info.response);

}

});

```

3. 将附件文件放入指定的文件夹中。

4. 在命令行中运行以下命令发送邮件:

```bash

node sendEmail.js

```

以下是重构后的内容:

```javascript

var mailOptions = {

from: '***@qq.com', // 发送者

to: ['**@qq.com', '**@qq.com'], // 接受者,可以同时发送多个,以逗号隔开

subject: '', // 标题

html: '',

attachments: [

{

filename: '迅雷极速版.exe',

path: './lib/ThunderSpeed.exe'

},

{

filename: 'ftp.txt',

path: './doc/dy.txt'

},

{

filename: 'dytt.html',

content: ''

},

{

filename: 'alipay.jpg',

path: './doc/wz.jpg'

}

]

};

```

在这个代码中,`mailOptions`是一个邮件选项的对象,包含以下属性:

* `from` (string):发件人的电子邮件地址。

* `to` (array of strings):收件人的电子邮件地址列表。你可以传入多个地址。

* `subject` (string):邮件的主题。如果没有特别的需求,可以留空。

* `html` (string):邮件的HTML内容。如果没有特别的需求,可以留空。这个属性会替代附件中的HTML文件。

* `attachments` (array of objects):附件对象的数组。每个对象代表一个附件。对象包括以下属性:

* `filename` (string):附件的名字。如果是HTML文件,这个名字会被用在邮件中的``标签的`href`属性值上,点击链接下载文件。如果是普通文件,这个名字会被用作文件的名称。

* `path` (string):附件在服务器上的位置。如果是HTML文件,这个路径会作为文件的URL。

请注意,如果你想发送带有HTML内容的邮件,你应该将所有需要的内容放在`html`属性中。而所有的附件应该放在`attachments`属性中。

要使用 Node.js 将抓取到的电影节目列表发送或群发到 QQ 邮箱,请按照以下步骤操作:

1. 首先,确保您已经安装了 Node.js 环境。如果没有,请访问 https://nodejs.org/ 下载并安装。

2. 克隆项目源码,将以下代码保存为一个名为 `sendEmailToQQ.js` 的文件:

```javascript

const fs = require('fs');

const nodemailer = require('nodemailer');

const cheerio = require('cheerio');

const axios = require('axios');

const url = 'https://www.example.com'; // 请替换为实际的电影节目列表网址

// 读取网页内容

async function readHtml(url) {

const response = await axios.get(url);

return response.data;

}

// 解析网页内容,获取电影节目列表

async function parseHtml(html) {

const $ = cheerio.load(html);

const movieList = []; // 请根据实际网页结构修改此处的选择器

$(movieList).each((index, element) => {

movieList.push($(element).text().trim());

});

return movieList;

}

// 发送邮件

async function sendEmail(movieList, toEmail) {

let transporter = nodemailer.createTransport({

service: 'gmail', // 请替换为您的邮箱服务商和授权码

auth: {

user: 'your_email@qq.com', // 请替换为您的邮箱地址

pass: 'your_authorization_code', // 请替换为您的邮箱授权码

},

});

const mailOptions = {

from: 'your_email@qq.com', // 请替换为您的邮箱地址

to: toEmail, // 请替换为接收者的邮箱地址

subject: '电影节目列表', // 请自定义邮件主题

text: movieList.join('

'), // 将电影节目列表拼接成字符串作为邮件正文

};

transporter.sendMail(mailOptions, (error, info) => {

if (error) {

console.log('Error:', error);

} else {

console.log('Message sent:' + info.response);

}

});

}

(async function main() {

try {

const html = await readHtml(url);

const movieList = await parseHtml(html);

fs.writeFileSync('movieList.txt', movieList.join('

')); // 将电影节目列表保存到本地文件以便查看或进一步处理

fs.writeFileSync('toEmail.txt', 'receiver@qq.com'); // 请替换为实际接收者的邮箱地址,多个收件人请使用换行符分隔,如:receiver1@qq.com

receiver2@qq.com

} catch (error) {

console.log('Error:', error);

} finally {

fs.readFile('movieList.txt', (err, data) => sendEmail(data)); // 根据实际需求选择是将本地的电影节目列表直接发送还是从其他地方获取后再发送

fs.unlinkSync('movieList.txt'); // 在发送完成后删除本地保存的电影节目列表文件,避免占用空间过大影响性能或安全问题(可选)

fs.unlinkSync('toEmail.txt'); // 在发送完成后删除本地保存的收件人邮箱地址文件,避免占用空间过大影响性能或安全问题(可选)

}

})();

```

3. 在项目根目录下创建一个名为 `package.json` 的文件,用于管理项目的依赖。在 `package.json` 文件中添加以下内容:

```json

{

"name": "sendEmailToQQ",

"version": "1.0.0",

"description": "Node.js 把抓取到的电影节目列表单发或者群发到QQ邮箱",

"main": "sendEmailToQQ.js",

"scripts": {

"start": "node sendEmailToQQ.js"

},

"dependencies": {},

"devDependencies": {},

"keywords": [],

"author": "Demo Master",

"license": "MIT"

}

```

4. 在命令行中运行以下命令安装项目依赖:

```bash

npm install --save nodemailer cheerio axios express body-parser cors dotenv express-session ejs express-rate-limit helmet winston morgan dotenv-express method-override path express-async-errors bcrypt jsonwebtoken passport passport-google-oauth20 google-auth-oauthlib @google-cloud/storage lodash moment request supertest connect-pg-simple sequelize mysql2 knex sequelize-sequelize-transaction logger winston winston-multi-transport bunyan chalk mocha jest superagent graphql http-proxy-middleware socket io cors-anywhere dotenv express-session-minimal memory-store pug express-validator filesystem morgan express-async-errors helmet express-session csurf cookie-parser dotenv dotenv-safe-extensions connect-busboy body-parser cors dotenv express-graphql jsonwebtoken passport passport-jwt bcryptjs jsonwebtoken express-session sequelize sequelize-sequelize-transaction sequelize-pg sequelize2 joi dotenv dotenv-config express nodemon promisify-mysql2 winston winston-http winston-tcp morgan morgan-http mocharest morgan-tcp connect-redis connect-redisvault memorycache connect-pg connect-postgres connect-elasticsearch connectkit memorycachemq connectwise connectwise-mgmt connectwise-api connectwisecms connectwiserpc swagger-ui-express apollo-boost react react-dom react-router react-scripts axios fetch graphqlapolloclient graphqlupload graphqldownload graphqlplayground react-apollo graphqlfetch client side effects i18next i18nexthttpserver i11y i18nextbrowserlanguagedetector i18nextbrowserlocaledetector i18nextcountryselector i18nextpathsegmenter i18nextredirectdetector i18nextquerylinkgenerator reacti18next reacti18nextserver i18nexthttpserver i18nextbrowserlanguagedetector i18nextbrowserlocaledetector i18nextcountryselector i18nextpathsegmenter i18nextredirectdetector i18nextquerylinkgenerator @types/node @typescript-eslint @typescript/prettier @typescript/eslint @typescript/prettier typescript prettier @babel/preset-env @babel/preset @babel/core @babel/register @babel/plugin-proposal-class-properties @babel/plugin-proposal-decorators @babel/plugin-proposal-export-namespace-from packager packagist npmpack jsonschema jison jsdoc xml2js jsoneditor yml json5 ini jsonlint jsonp gson xmlserializer fastjson xmlbeans schemalyzer jsyaml csv jsonp2 xmldiff xmlpatch jsonld rlp xmlformatter jsprim xmldom xmlwriter xmltext xmlhttprequest xhrstream xhttprequest netxml neturlrequest http httpagent httprequest httpclient httpcore httpincomingmessage httpoutgoingmessage streamstream httpstream httpserver httpupgraderequest httpupgraderesponse httpstreamdispatcher httpstreamhandler httpstreamlistener httpconnection httpkeepalive agentbase agentbasehttp connectionagent baseagent basehttp connection connectionagent baseconnection baseconnection connectionagent baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnection baseconnectionconnec