generateHTML.js 3.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130
  1. const { PATH_FILES } = require('../config')
  2. const logger = require('../log/index')
  3. const puppeteer = require('puppeteer');
  4. const fs = require('fs')
  5. const path = require('path')
  6. // 生成
  7. async function initBrowser () {
  8. logger.log.debug('启动', new Date().toLocaleString())
  9. return await puppeteer.launch({
  10. headless: true,
  11. args: ['--no-sandbox', '--disable-setuid-sandbox']
  12. });
  13. }
  14. let browser = null
  15. function checkCache (fPath) {
  16. try {
  17. const fStat = fs.statSync(fPath)
  18. if (fStat) {
  19. const isFile = fStat.isFile()
  20. if (isFile) {
  21. return fPath
  22. }
  23. }
  24. return false
  25. } catch (err) {
  26. return false
  27. }
  28. }
  29. function wait(ms) {
  30. return new Promise((resolve, reject) => {
  31. setTimeout(() => {
  32. console.log("Done waiting");
  33. resolve(ms)
  34. }, ms)
  35. })
  36. }
  37. async function createHTMLOfURL (url, config = {}) {
  38. if (!browser) {
  39. browser = await initBrowser()
  40. }
  41. config = Object.assign( {
  42. filename: '',
  43. dir: '',
  44. nocache: false,
  45. width: '950px',
  46. height: '1360px',
  47. margin: {
  48. top: 0,
  49. bottom: 0
  50. },
  51. }, config)
  52. // 文件路径
  53. const outPath = path.join(PATH_FILES, config.dir)
  54. const outConfig = Object.assign({path: `${config.filename}.html`, width: config.width, height: config.height,printBackground: true }, config)
  55. outConfig.path = path.join(outPath, outConfig.path)
  56. const outFilePath = outConfig.path.slice(0, outConfig.path.lastIndexOf('/'))
  57. if (!fs.existsSync(outFilePath)) {
  58. fs.mkdirSync(outFilePath);
  59. }
  60. // 检查缓存
  61. if (!config.nocache) {
  62. const result = checkCache(outConfig.path)
  63. if (result) {
  64. logger.log.debug('命中缓存文件')
  65. return result
  66. }
  67. }
  68. const page = await browser.newPage();
  69. try {
  70. await page.setDefaultNavigationTimeout(0)
  71. page.on('console', async (message) => {
  72. const args = await Promise.all(message.args().map(arg => arg.jsonValue()));
  73. logger.log.debug(`page log: ${message.type()}: ${message.text()} args: ${JSON.stringify(args)}`);
  74. });
  75. await page.on('response', (response) => {
  76. if (response.status() !== 200) {
  77. logger.log.debug(`Res error: ${response.status()} ${response.url()}`)
  78. }
  79. });
  80. await page.goto(url, {waitUntil: 'networkidle2'});
  81. // 在网页上执行一些操作,可能触发了 console.log
  82. await page.evaluate(() => {
  83. console.warn('Hello from the page!');
  84. });
  85. await wait(config.delay || 1000)
  86. logger.log.debug('等待生成', new Date().toLocaleString())
  87. const html = await page.evaluate(() => {
  88. const element = document.querySelector('.analysis-report') || document.querySelector('body');
  89. return element.outerHTML;
  90. });
  91. // 保存生成的HTML到文件
  92. const fs = require('fs');
  93. fs.writeFileSync(outConfig.path, html);
  94. await page.close();
  95. logger.log.debug('当前时间', new Date().toLocaleString())
  96. return outConfig.path
  97. } catch (e) {
  98. logger.log.debug(e)
  99. await page.close();
  100. }
  101. }
  102. module.exports = createHTMLOfURL