Vite项目打包生成dist.zip方法

使用自定义插件(推荐)

步骤1:安装依赖

bash

复制

复制代码
npm install jszip -D

步骤2:创建插件文件

在项目根目录新建zip.js(或createZip.ts,若使用TypeScript),写入以下代码:

javascript

复制

ini 复制代码
const path = require('path');
const fs = require('fs');
const JSZip = require('jszip');

const plugin = (fileName = 'dist', outputPath) => {
  const output = outputPath || path.resolve(__dirname, './dist');
  fileName += '.zip';

  const makeZip = () => {
    const zip = new JSZip();
    const distPath = path.resolve(output);

    // 递归读取文件夹并添加到Zip
    const readDir = (zipInstance, dirPath) => {
      const files = fs.readdirSync(dirPath);
      files.forEach(file => {
        const filePath = path.join(dirPath, file);
        const stats = fs.statSync(filePath);
        if (stats.isDirectory()) {
          const folder = zipInstance.folder(file);
          readDir(folder, filePath);
        } else {
          zipInstance.file(file, fs.readFileSync(filePath));
        }
      });
    };

    // 删除已存在的Zip文件
    const removeExistingZip = () => {
      const zipPath = path.join(distPath, '../', fileName);
      if (fs.existsSync(zipPath)) fs.unlinkSync(zipPath);
    };

    // 生成Zip内容并写入文件
    readDir(zip, distPath);
    zip.generateAsync({
      type: 'nodebuffer',
      compression: 'DEFLATE',
      compressionOptions: { level: 9 }
    }).then(content => {
      const destPath = path.join(distPath, '../', fileName);
      removeExistingZip();
      fs.writeFileSync(destPath, content);
    });
  };

  return {
    name: 'vite-plugin-auto-zip',
    apply: 'build',
    closeBundle: makeZip
  };
};

module.exports = plugin;

步骤3:在Vite配置中引入插件

修改vite.config.js(或vite.config.ts):

javascript

复制

javascript 复制代码
import { defineConfig } from 'vite';
import vue from '@vitejs/plugin-vue';
import zipPlugin from './zip';

export default defineConfig({
  plugins: [
    vue(),
    zipPlugin() // 可传参自定义文件名,如 zipPlugin('myapp', './custom-dist')
  ],
  build: {
    outDir: 'dist', // 可选:修改输出目录名:cite[3]:cite[8]
  }
});

步骤4:执行打包

bash

复制

arduino 复制代码
npm run build

如果只想在开发环境development)下启用 ZIP 打包功能,而在生产环境production)下禁用,可以修改 Vite 插件逻辑,使其仅在 vite devvite build --mode development 时生效。以下是具体实现方法:


方法 1:基于 mode 动态启用插件

1. 修改插件逻辑(createZip.js

javascript

复制

ini 复制代码
import path from 'path';
import fs from 'fs';
import JSZip from 'jszip';

export default function createZipPlugin(options = {}) {
  const {
    fileName = 'dist',
    outputPath,
    enabled = process.env.NODE_ENV === 'development' // 默认开发环境启用
  } = options;

  if (!enabled) {
    // 如果禁用,返回一个空插件
    return {
      name: 'vite-plugin-auto-zip',
      apply: 'build',
      closeBundle: () => {} // 空函数
    };
  }

  const output = outputPath || path.resolve(process.cwd(), './dist');
  const zipFileName = `${fileName}.zip`;

  const makeZip = () => {
    const zip = new JSZip();
    const distPath = path.resolve(output);

    // 递归读取文件夹
    const readDir = (zipInstance, dirPath) => {
      const files = fs.readdirSync(dirPath);
      files.forEach(file => {
        const filePath = path.join(dirPath, file);
        const stats = fs.statSync(filePath);
        if (stats.isDirectory()) {
          const folder = zipInstance.folder(file);
          readDir(folder, filePath);
        } else {
          zipInstance.file(file, fs.readFileSync(filePath));
        }
      });
    };

    // 生成 ZIP
    readDir(zip, distPath);
    zip.generateAsync({
      type: 'nodebuffer',
      compression: 'DEFLATE',
      compressionOptions: { level: 9 }
    }).then(content => {
      const destPath = path.join(distPath, '../', zipFileName);
      if (fs.existsSync(destPath)) fs.unlinkSync(destPath);
      fs.writeFileSync(destPath, content);
    });
  };

  return {
    name: 'vite-plugin-auto-zip',
    apply: 'build',
    closeBundle: makeZip
  };
}

2. 在 vite.config.js 中动态配置

javascript

复制

javascript 复制代码
import { defineConfig } from 'vite';
import vue from '@vitejs/plugin-vue';
import createZipPlugin from './createZip';

export default defineConfig(({ mode }) => ({
  plugins: [
    vue(),
    createZipPlugin({
      enabled: mode === 'development' // 仅开发模式启用
    })
  ],
  build: {
    outDir: 'dist'
  }
}));
相关推荐
wuhen_n13 分钟前
动态组件与 keep-alive:如何优化页面切换体验与性能?
前端·javascript·vue.js
wuhen_n15 分钟前
插槽的作用域与分发:如何让组件更灵活、可定制?
前端·javascript·vue.js
IT_陈寒22 分钟前
Vite凭什么比Webpack快10倍?5个核心优化原理大揭秘
前端·人工智能·后端
gyx_这个杀手不太冷静39 分钟前
OpenCode 进阶使用指南(第三章:MCP 集成)
前端·ai编程
摸鱼的春哥42 分钟前
你适合养龙虾🦞吗?4类人不适合2类适合
前端·javascript·后端
Moment1 小时前
Agent 开发本质上就是高级点的 CRUD
前端·后端·面试
恋猫de小郭2 小时前
OpenAI 亲自教你如何构建可靠 AI 代码,从古法编程转向 Agnet 编程,或者 PUA 你的 AI
前端·人工智能·ai编程
程序员爱钓鱼3 小时前
Go错误处理全解析:errors包实战与最佳实践
前端·后端·go
清汤饺子11 小时前
OpenClaw 本地部署教程 - 从 0 到 1 跑通你的第一只龙虾
前端·javascript·vibecoding
爱吃的小肥羊13 小时前
比 Claude Code 便宜一半!Codex 国内部署使用教程,三种方法任选一!
前端