<output id="qn6qe"></output>

    1. <output id="qn6qe"><tt id="qn6qe"></tt></output>
    2. <strike id="qn6qe"></strike>

      亚洲 日本 欧洲 欧美 视频,日韩中文字幕有码av,一本一道av中文字幕无码,国产线播放免费人成视频播放,人妻少妇偷人无码视频,日夜啪啪一区二区三区,国产尤物精品自在拍视频首页,久热这里只有精品12

      Nuxt.js 生成sitemap站點地圖文件

      Nuxt.js 生成sitemap站點地圖文件

      背景介紹

      ? 使用nuxt框架生成靜態文件支持SEO優化,打包之后需要生成一個 sitemap.xml 文件方便提交搜索引擎進行收錄。官網有提供一個插件sitemap 但是如果是動態路由需要手動一個個配置比較麻煩,無法自動檢索生成。所以自己編寫一個生成 sitemap 模塊

      準備工作

      創建nuxt項目,參考中文官網。安裝JavaScript模板ejs工具

      $ npm install ejs
      

      相關網站

      sitemap模塊

      項目根目錄創建 modules 目錄,以及對應文件,詳細文件內容放在文末。

      ├─modules
      │  └─robots.ejs // robots模板
      │  └─sitemap.js // 站點地圖js
      │  └─template.ejs //sitemap 模板
      

      配置 nuxt.config.js

      modules 數組增加以下內容 modules/sitemap 剛才自定義模塊,excludes 需要排除的目錄,hostname 站點域名

      nuxt.config.js

      export default {
        ...省略
        // Modules: https://go.nuxtjs.dev/config-modules
        modules: [
          ...省略,
          ['modules/sitemap',
            {
              excludes: ['_nuxt', 'img'],
              hostname: 'https://www.example.com'
            }
          ],
        ],
      }
      

      執行命令生成靜態資源

      $npm run generate
      

      打開項目根目錄下dist(默認輸出路徑),會多出兩個文件

      ├─robots.txt
      ├─sitemap.xml
      

      結果展示

      sitemap

      robots

      官方示例 modules

      編寫自己的模塊

      模塊就是函數。它們可以打包為 npm 模塊或直接包含在項目源代碼中。

      nuxt.config.js

      export default {
        exampleMsg: 'hello',
        modules: [
          // Simple usage
          '~/modules/example',
          // Passing options directly
          ['~/modules/example', { token: '123' }]
        ]
      }
      

      modules/example.js

      export default function ExampleModule(moduleOptions) {
        console.log(moduleOptions.token) // '123'
        console.log(this.options.exampleMsg) // 'hello'
      
        this.nuxt.hook('ready', async nuxt => {
          console.log('Nuxt is ready')
        })
      }
      
      // REQUIRED if publishing the module as npm package
      module.exports.meta = require('./package.json')
      

      1) ModuleOptions

      moduleOptionsmodules 這是用戶使用數組傳遞的對象 。我們可以用它來定制它的行為。

      頂級選項

      有時,如果我們可以在注冊模塊時使用頂級選項會更方便 nuxt.config.js。這使我們能夠組合多個選項源。

      nuxt.config.js

      export default {
        modules: [['@nuxtjs/axios', { anotherOption: true }]],
      
        // axios module is aware of this by using `this.options.axios`
        axios: {
          option1,
          option2
        }
      }
      

      2) this.options

      this.options:您可以使用此參考直接訪問 Nuxt 選項。nuxt.config.js 這是分配有所有默認選項的用戶內容 。它可用于模塊之間的共享選項。

      模塊.js

      export default function (moduleOptions) {
        // `options` will contain option1, option2 and anotherOption
        const options = Object.assign({}, this.options.axios, moduleOptions)
      
        // ...
      }
      

      modules文件

      modules/robots.ejs

      # robots.txt
      User-agent: Baiduspider
      Disallow:
      User-agent: Sosospider
      Disallow:
      User-agent: sogou spider
      Disallow:
      User-agent: YodaoBot
      Disallow:
      User-agent: Googlebot
      Disallow:
      User-agent: Bingbot
      Disallow:
      User-agent: Slurp
      Disallow:
      User-agent: Teoma
      Disallow:
      User-agent: ia_archiver
      Disallow:
      User-agent: twiceler
      Disallow:
      User-agent: MSNBot
      Disallow:
      User-agent: Scrubby
      Disallow:
      User-agent: Robozilla
      Disallow:
      User-agent: Gigabot
      Disallow:
      User-agent: googlebot-image
      Disallow:
      User-agent: googlebot-mobile
      Disallow:
      User-agent: yahoo-mmcrawler
      Disallow:
      User-agent: yahoo-blogs/v3.9
      Disallow:
      User-agent: psbot
      Disallow:
      Disallow: /bin/
      Disallow: /js/
      Disallow: /img/
      Sitemap: <%= hostname %>/sitemap.xml
      

      modules/sitemap.js

      /**
       * @description 生成 sitemap robots 模塊
       * @author 方圓百里
       * @time 2023年10月12日
       */
      
      const path = require('path');
      const fs = require('fs');
      const ejs = require('ejs');
      /**
       * @description 獲取當前目錄下載的所有路徑 -同步
       * @author 方圓百里
       *
       * @param {String} dir 文件路徑
       * @returns {Array} 返回路徑數組
       */
      const loadFiles = (dir) => {
        try {
          const data = fs.readdirSync(dir);
          return data;
        } catch (e) {
          console.error('獲取目錄路徑異常', e)
          return undefined;
        }
      }
      
      /**
       * @description 獲取文件信息
       * @author 方圓百里
       *
       * @param {String} dir 文件路徑
       * @returns {Array} 返回路徑數組
       */
      const statFile = (full_path) => {
        try {
          const stat = fs.statSync(full_path);
          stat.path = full_path;
          return stat;
        } catch (e) {
          console.error('獲取目錄路徑異常', e)
          return undefined;
        }
      }
      
      /**
       * @description 遞歸處理文件路徑
       * @author 方圓百里
       *
       * @param {String} dir 文件路徑
       * @param {String} list 文件信息數組
       * @returns {Array} 返回路徑數組
       */
      const handleFiles = (dir, list = [], excludes) => {
        // 1、加載當前目錄下所有路徑,包含文件夾和文件
        const data = loadFiles(dir);
        if (data) {
          data.forEach(item => {
            if (!excludes.includes(item)) {
              // 2、拼接絕對路徑
              const absolutePath = path.join(dir, item)
              // 3、獲取文件基本信息
              const stat = statFile(absolutePath);
              // 4、如果是文件,處理基本信息
              if (stat.isFile()) {
                list.push({
                  size: stat.size,
                  time: stat.ctime,
                  ...path.parse(stat.path)
                })
              } else { // 5、目錄遞歸進行處理
                handleFiles(stat.path, list, excludes);
              }
            }
          })
        }
        return list;
      }
      
      /**
       * @description 格式化日期
       * @author 方圓百里
       *
       * @param {Date} date 日期
       * @returns {String} 2023-10-12
       */
      const formatYear = (date) => {
        // 獲取年、月和日
        const year = date.getFullYear();
        const month = (date.getMonth() + 1).toString().padStart(2, '0'); // 月份從0開始,需要加1,同時確保兩位數格式
        const day = date.getDate().toString().padStart(2, '0'); // 確保兩位數格式
        // 格式化日期
        return `${year}-${month}-${day}`;
      }
      
      /**
       * @description 生成站點地圖
       * @author 方圓百里
       *
       * @param {String} dist 打包后文件路徑
       * @param {String} hostname 主機名稱
       * @param {Array} excludes 排除路徑
       *
       */
      const generateSitemap = (dist, hostname, excludes) => {
        const data = handleFiles(dist, [], excludes)
        const set = new Set();
        for (var i = 0; i < data.length; i++) {
          const f = data[i];
          if (f.ext === '.html') {
            const relative = f.dir.replace(dist, "")
            if (relative) {
              const paths = relative.split(path.sep);
              let loc = hostname;
              for (var x = 1; x < paths.length; x++) {
                loc += "/" + paths[x];
              }
              set.add({
                loc: loc,
                time: formatYear(f.time)
              });
            }
          }
        }
        // 讀取模板文件
        const template = fs.readFileSync('modules/template.ejs', 'utf-8');
        // 提供模板數據
        const datas = {
          urls: set
        };
        // 使用模板引擎渲染模板
        const renderedContent = ejs.render(template, datas);
        // 寫入生成的文件
        fs.writeFileSync(path.join(dist, 'sitemap.xml'), renderedContent);
        console.log('sitemap.xml 生成成功!');
      
        const robotsRendered = ejs.render(fs.readFileSync('modules/robots.ejs', 'utf-8'), {
          hostname
        });
        // 寫入生成的文件
        fs.writeFileSync(path.join(dist, 'robots.txt'), robotsRendered);
        console.log('robots.txt 生成成功!');
      }
      export default function ExampleModule(moduleOptions) {
        const dist = this.options.generate?.dir || 'dist'; // 打包輸出路徑
        const hostname = moduleOptions.hostname || 'https://www.example.com'; // 主機名稱
        const excludes = moduleOptions.excludes || ['.nuxt']; // 排除路徑
        console.log('打包輸出路徑:=====>', dist)
        console.log('主機名稱:=====>', hostname)
        console.log('排除路徑:=====>', excludes)
      
        this.nuxt.hook('generate:done', async generator => {
          // 這將在Nuxt生成頁面之之后調用
          console.log('執行 generate 完成')
          generateSitemap(dist, hostname, excludes)
      
        })
      }
      
      // 將模塊發布為npm包
      module.exports.meta = require('../package.json')
      
      

      modules/template.ejs

      <?xml version="1.0" encoding="UTF-8"?>
      <urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9" xmlns:news="http://www.google.com/schemas/sitemap-news/0.9"
        xmlns:xhtml="http://www.w3.org/1999/xhtml" xmlns:mobile="http://www.google.com/schemas/sitemap-mobile/1.0"
        xmlns:image="http://www.google.com/schemas/sitemap-image/1.1"
        xmlns:video="http://www.google.com/schemas/sitemap-video/1.1">
        <url>
          <% urls.forEach(function(item) { %>
             <loc><%= item.loc %></loc>
             <lastmod><%= item.time %></lastmod>
             <changefreq>monthly</changefreq>
             <priority>0.8</priority>
          <% }); %>
        </url>
      </urlset>
      
      posted @ 2023-10-12 15:56  天葬  閱讀(1402)  評論(0)    收藏  舉報
      主站蜘蛛池模板: 欧美日本激情| 日本一区二区三区免费播放视频站| 色综合五月伊人六月丁香| 人妻少妇偷人一区二区| 欧洲精品码一区二区三区| 久久精品人人看人人爽| 国产免费高清69式视频在线观看| 香港经典a毛片免费观看播放| 久久一区二区三区黄色片| 国产一区二区日韩在线| 国产盗摄xxxx视频xxxx| 99久久国产一区二区三区| 亚洲精品日韩中文字幕| 宁武县| 日本一本无道码日韩精品| 亚洲精品一区二区动漫| 中国大陆高清aⅴ毛片| 国产高清精品在线一区二区| 国产 亚洲 制服 无码 中文| 国产av一区二区三区综合| 精品国产熟女一区二区三区| 亚洲精品天堂一区二区| 亚洲综合久久精品国产高清| 99久久久无码国产精品免费| 国产福利酱国产一区二区| 四虎国产精品久久免费地址| 欧美三级不卡在线观线看高清| 国产精品综合色区av| 色狠狠综合天天综合综合| 孕妇怀孕高潮潮喷视频孕妇| 日韩精品一区二区三区蜜臀| A毛片终身免费观看网站| 亚洲精品国产中文字幕| 国产午夜美女福利短视频| 国产免费踩踏调教视频| 视频一区视频二区制服丝袜| 九九久久人妻精品一区色| 久久精品久久电影免费理论片| 99久久精品国产一区二区蜜芽| av无码小缝喷白浆在线观看| 好吊视频在线一区二区三区|