Windows下YUICompress实现js、css混淆压缩

news2024/11/26 7:51:57

首先,我们针对Linux下的部分命令进行Windows系统的对应实现

ls————cmd /c dir/b
rm————cmd /c del
mv————cmd /c move
pwd————cmd /c chdir
注:cmd /c是执行完命令后关闭命令行窗口、cmd /k是执行完命令后不关闭命令行窗口、cmd /c start是会打开新窗口,关闭旧窗口、cmd /c start是会打开新窗口,不关闭旧窗口

也可以将上述命令做成bat文件,放到Windows/System32目录下,例如,如下文件命名为ls.bat,放到对应目录下,cmd执行ls命令

@echo off
dir

在这里插入图片描述
接下来,全局安装JAVASCRIPT_OBFUSCATOR,需要提前准备好Node环境
在这里插入图片描述

#安装
npm install javascript-obfuscator -g
#检查是否安装成功
javascript-obfuscator -v

然后在系统环境变量指定path,我这里是npm安装,因此,找到npm路径,在系统用户变量的path里,例如C:\Users\zy_ys\AppData\Roaming\npm
在这里插入图片描述
加到系统变量的path里
在这里插入图片描述
还需要准备YUI压缩使用的jar包,这里使用2.4.8版本,下载地址,提取码qc1j,接下来,对应本地项目,改造如下代码,具体改造内容为项目路径、jar包路径、压缩文件路径等,完整代码如下

import org.apache.commons.lang3.StringUtils;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Attribute;
import org.jsoup.nodes.Attributes;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;

import java.io.*;
import java.nio.charset.StandardCharsets;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * 通过压缩JS文件、更改日期工具类
 * 需要系统 MacOS
 * 需要安装的软件
 * yui compressor:安装方式 下载jar包 使用时指定包所在路径使用命令即可
 * uglifyJs: npm 或者 brew 安装
 * javascript-obfuscator npm安装
 *
 * @author zwf
 * @date 20190703
 */
public class CompressCommand {
	private static final String encoding = "utf-8";
	private static final String[] SUFFIXARRAY = {".js", ".css"};
	private static final String[] JS_SUFFIXARRAY = {".js"};
	private static final String TEMP = ".temp";
	/**
	 * YUI_PATH 压缩使用的jar包路径
	 */
	private static final String YUI_PATH = "C:\\Users\\zy_ys\\Desktop\\yuicompressor-2.4.8.jar";

	/**
	 * JAVASCRIPT_OBFUSCATOR 命令所在路径
	 */
	private static final String JAVASCRIPT_OBFUSCATOR_CMD = "javascript-obfuscator";
	/**
	 * 项目根路径开始的js路径
	 */
	private static final String RESOURCES_PATH = "project\\src\\main\\resources\\static\\";
	/**
	 * 项目根路径开始的HTML路径
	 */
	private static final String RESOURCES_HTML_PATH = "project\\src\\main\\resources\\templates\\";
	/**
	 * JS的文件夹名称
	 */
	private static final String[] CSS_JS_DIRECTION = {"js\\aaa", "js\\bbb", "js\\ccc","js\\login","js\\ddd", "js\\eee", "js\\fff", "js\\ggg", "css"};
	/**
	 * HTML的文件夹名称
	 */
	private static final String[] DIRECTION_HTML = {"aaa", "download", "error", "ccc", "ddd", "bbb", "eee", "fff"};

	/**
	 *
	 */
	private static final String DATE_STAMP = System.currentTimeMillis() + "";
	/**
	 * 所有未压缩JS的集合
	 */
	private static List<String> RESOURCE_LIST = new ArrayList<>();
	/**
	 * 所有的中间文件HTML
	 */
	private static List<String> TEMP_HTML_LIST = new ArrayList<>();
	/**
	 * 项目跟路径
	 */
	private static String PROJECT_PATH = "";

	private static String CSS_COMPRESS_ONLY = "NO";

	static {
		Runtime runtime = Runtime.getRuntime();
		BufferedReader bufferedReader = null;
		try {
			Process process = runtime.exec("cmd /c chdir");
			if (process.waitFor() == 0) {
				bufferedReader = new BufferedReader(new InputStreamReader(process.getInputStream()));
				PROJECT_PATH = bufferedReader.readLine();
				System.out.println(PROJECT_PATH);
			}
			if (StringUtils.isBlank(PROJECT_PATH)) {
				System.err.println("获取当前项目路径操作失败, 停止操作!");
				System.exit(-1);
			}
		} catch (Exception ex) {
			ex.printStackTrace();
		} finally {
			if (null != bufferedReader) {
				try {
					bufferedReader.close();
				} catch (IOException e) {
					e.printStackTrace();
				}
			}
		}
	}

	enum STEP {
		/**
		 * 第一步:删除 min.js 文件
		 */
		STEP_ONE_RM_OLD_MIN_JS,
		/**
		 * 第二步:生成新的 min.js 文件
		 */
		STEP_TWO_CREATE_NEW_MIN_JS,
		/**
		 * 第三步: 生成htm中间文件
		 */
		STEP_THREE_CREATE_COPY_TEMPLATE,
		/**
		 * 第四步: 替换中间文件的min.js
		 */
		STEP_FOUR_REPLACE_MIN_JS,
		/**
		 * 第五步: 还原html文件
		 */
		STEP_FIVE_DELETE_TEMPLATE,

	}

	enum CompressObfuscator {
		YUI_COMPRESSOR,
		UGLIFY_JS,
		JAVASCRIPT_OBFUSCATOR
	}

	enum EVN {
		DEBUG,
		PUBLISH,
	}

	public static void main(String[] args) throws Exception {
		EVN evn = EVN.DEBUG;
		//DEBUG是初始化,PUBLISH是混淆压缩
		System.out.println(" 请输入你需要操作的模式? DEBUG 或者 PUBLISH ");
		Scanner scanner = new Scanner(System.in);
		String command = scanner.nextLine();
		if ("debug".equalsIgnoreCase(command)) {
			evn = EVN.DEBUG;
		} else if ("publish".equalsIgnoreCase(command)) {
			evn = EVN.PUBLISH;
		} else {
			System.exit(0);
		}

		switch (evn) {
			case DEBUG:
				// 还原html文件中的js文件
				devOps();
				break;
			case PUBLISH:
				masterOps();
				break;
		}

	}

	enum DevStep {
		RM_MIN_JS,
		RP_TEMPLATE_COPY,
		RM_TEMPLATE,

	}

	private static void devOps() throws Exception {
		// 第一步: 删除min.js
		List<String> commandList = initRmJsCommandList();
		execDevCommand(commandList, DevStep.RM_MIN_JS);
		// 第二步: 生成中间文件
		List<String> commandList1 = initTempLateCommandList();
		execDevCommand(commandList1, DevStep.RP_TEMPLATE_COPY);
		// 第三步: 替换js
		reverseReplaceJsInHtml();
		// 第四步: 删除html中间文件
		List<String> backCommand = initDelTemplateList();
		execDevCommand(backCommand, DevStep.RM_TEMPLATE);
	}

	private static void execDevCommand(List<String> commandList, DevStep devStep) {
		switch (devStep) {
			case RM_MIN_JS:
				System.out.println("开始删除min.js文件-----");
				execute(commandList);
				System.out.println("结束删除min.js文件-----");
				break;
			case RP_TEMPLATE_COPY:
				System.out.println("开始生成HTML中间文件-----");
				execute(commandList);
				System.out.println("结束生成HTML中间文件-----");
			case RM_TEMPLATE:
				System.out.println("开始删除html中间文件");
				execute(commandList);
				System.out.println("结束删除html中间文件");
				break;

		}
	}

	private static void masterOps() throws Exception {
		// step 1 :初始化min.js删除命令集合
		List<String> rmCmdList = initRmJsCommandList();
		execCommand(rmCmdList, STEP.STEP_ONE_RM_OLD_MIN_JS);
		//step 2: 压缩文件,生成新的min.js文件, 如使用yui压缩, 注释掉第一行compressJSCommandList
		List<String> compressJSCommandList = getCompressCommandList(CompressObfuscator.JAVASCRIPT_OBFUSCATOR);
		List<String> compressCssCommandList = getCompressCommandList(CompressObfuscator.YUI_COMPRESSOR);
		execCommand(compressJSCommandList, STEP.STEP_TWO_CREATE_NEW_MIN_JS);
		execCommand(compressCssCommandList, STEP.STEP_TWO_CREATE_NEW_MIN_JS);
		//step 3: 生成html中间文件
		List<String> tempTempLateCommandList = initTempLateCommandList();
		execCommand(tempTempLateCommandList, STEP.STEP_THREE_CREATE_COPY_TEMPLATE);
		//step 4: 替换中间文件的min.js
		replaceJsInHtml();
		//step 5: 恢复HTML文件
		List<String> backCommand = initDelTemplateList();
		execCommand(backCommand, STEP.STEP_FIVE_DELETE_TEMPLATE);
	}

	private static List<String> getCompressCommandList(CompressObfuscator javascriptObfuscator) throws Exception {
		switch (javascriptObfuscator) {
			case YUI_COMPRESSOR:
				return initCommandList(YUI_PATH);
			case UGLIFY_JS:
				CSS_COMPRESS_ONLY = "YES";
				return initUglifyJsCommandList();
			case JAVASCRIPT_OBFUSCATOR:
				CSS_COMPRESS_ONLY = "YES";
				return initJavascriptObfuscatorCommandList();
			default:
				throw new RuntimeException("出错了,停止吧!");
		}
	}


	private static void execCommand(List<String> commandList, STEP step) throws Exception {
		switch (step) {
			case STEP_ONE_RM_OLD_MIN_JS:
				System.out.println("开始清理旧的min.js文件---");
				execute(commandList);
				System.out.println("清理旧的min.js文件结束");
				break;
			case STEP_TWO_CREATE_NEW_MIN_JS:
				System.out.println("开始生成新的min.js文件--");
				execute(commandList);
				System.out.println("结束生成新的min.js文件--");
				break;
			case STEP_THREE_CREATE_COPY_TEMPLATE:
				System.out.println("开始生成新的html中间文件--");
				execute(commandList);
				System.out.println("结束生成新的html中间文件--");
				break;
			case STEP_FIVE_DELETE_TEMPLATE:
				System.out.println("开始还原html文件--");
				execute(commandList);
				System.out.println("结束还原html文件--");
				break;
			default:
		}
	}

	private static List<String> initUglifyJsCommandList() throws Exception {
		List<String> cmdList = new ArrayList<>();
		for (String directionJ : CSS_JS_DIRECTION) {
			String lsCmd = "ls " + PROJECT_PATH + "/" + RESOURCES_PATH + directionJ;
			Process process = Runtime.getRuntime().exec(lsCmd);
			InputStream inputStream = null;
			BufferedReader bufferedReader = null;
			if (process.waitFor() == 0) {
				inputStream = process.getInputStream();
				bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
				String line = null;
				while ((line = bufferedReader.readLine()) != null) {
					String suffix = line.substring(line.lastIndexOf("."));

					List<String> suffixList = Arrays.asList(JS_SUFFIXARRAY);
					if (suffixList.contains(suffix) && !line.endsWith("-min" + suffix)) {
						StringBuffer _path = new StringBuffer();
						_path.append(PROJECT_PATH).append("/");
						_path.append(RESOURCES_PATH).append(directionJ).append("/").append(line).append(" ");
						RESOURCE_LIST.add(_path.toString());

						StringBuffer sb = new StringBuffer();
						sb.append("uglifyjs ");
						sb.append(_path.toString()).append(" ");
						sb.append("-c ");
						sb.append("--ie8 ");
						sb.append("-m ");
						sb.append("-o").append(" ");
						sb.append(PROJECT_PATH).append("/");
						sb.append(RESOURCES_PATH).append(directionJ).append("/").append(line.replace(suffix, "-" + DATE_STAMP + "-min" + suffix));
						cmdList.add(sb.toString());
					}
				}
			}
		}
		System.out.println("初始化压缩命令成功");
		return cmdList;
	}

	private static List<String> initJavascriptObfuscatorCommandList() throws Exception {

		List<String> cmdList = new ArrayList<>();
		for (String directionJ : CSS_JS_DIRECTION) {
			String lsCmd = "cmd /c dir/b " + PROJECT_PATH + "\\" + RESOURCES_PATH + directionJ;
			Process process = Runtime.getRuntime().exec(lsCmd);
			InputStream inputStream = null;
			BufferedReader bufferedReader = null;
			if (process.waitFor() == 0) {
				inputStream = process.getInputStream();
				bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
				String line = null;
				while ((line = bufferedReader.readLine()) != null) {
					String suffix = line.substring(line.lastIndexOf("."));

					List<String> suffixList = Arrays.asList(JS_SUFFIXARRAY);
					if (suffixList.contains(suffix) && !line.endsWith("-min" + suffix)) {
						StringBuffer _path = new StringBuffer();
						_path.append(PROJECT_PATH).append("\\");
						_path.append(RESOURCES_PATH).append(directionJ).append("\\").append(line).append(" ");
						RESOURCE_LIST.add(_path.toString());

						StringBuffer sb = new StringBuffer();
						sb.append(" cmd /c ");
						sb.append(JAVASCRIPT_OBFUSCATOR_CMD).append(" ");
						sb.append(_path.toString()).append(" ");
						sb.append("--output").append(" ");
						sb.append(PROJECT_PATH).append("\\");
						sb.append(RESOURCES_PATH).append(directionJ).append("\\").append(line.replace(suffix, "-" + DATE_STAMP + "-min" + suffix));
						cmdList.add(sb.toString());
					}
				}
			}
		}
		System.out.println("初始化压缩命令成功");
		return cmdList;
	}

	private static List<String> initDelTemplateList() throws Exception {
		List<String> cmdList = new ArrayList<>();
		for (String htmlFilePath : TEMP_HTML_LIST) {
			StringBuffer sb = new StringBuffer();
			sb.append("cmd /c del ").append(" ");
			sb.append(htmlFilePath).append(" ");
			cmdList.add(sb.toString());
		}
		return cmdList;
	}

	private static List<String> initTempLateCommandList() throws Exception {
		List<String> cmdList = new ArrayList<>();
		for (String directionH : DIRECTION_HTML) {
			String lsCmd = "cmd /c dir/b " + PROJECT_PATH + "\\" + RESOURCES_HTML_PATH + directionH;
			Runtime runtime = Runtime.getRuntime();
			Process process = runtime.exec(lsCmd);
			if (process.waitFor() == 0) {
				InputStream inputStream = null;
				BufferedReader bufferedReader = null;
				try {
					inputStream = process.getInputStream();
					bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
					String line = null;
					while ((line = bufferedReader.readLine()) != null) {
						if (line.endsWith(".html")) {
							StringBuilder stringBuilder = new StringBuilder();
							stringBuilder.append("cmd /c move").append(" ");
							stringBuilder.append(PROJECT_PATH).append("\\");
							stringBuilder.append(RESOURCES_HTML_PATH).append(directionH).append("\\").append(line).append(" ");
							StringBuffer stringBuffer = new StringBuffer();
							stringBuffer.append(PROJECT_PATH).append("\\");
							stringBuffer.append(RESOURCES_HTML_PATH).append(directionH).append("\\").append(line).append(TEMP).append(" ");
							TEMP_HTML_LIST.add(stringBuffer.toString());
							cmdList.add(stringBuilder.append(stringBuffer.toString()).toString());
						}
					}
				} catch (Exception ex) {
					ex.printStackTrace();
				} finally {
					if (inputStream != null) {
						inputStream.close();
					}
					if (bufferedReader != null) {
						bufferedReader.close();
					}
				}
			}
		}
		return cmdList;
	}


	private static synchronized void execute(List<String> commandList) {
		long beginTime = System.currentTimeMillis();
		int count = 0;
		//这里实际定义的是环境变量的地址,我们配置了path,可以忽略
		String[] envp = new String[] {"PATH=/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin"};
		for (String command : commandList) {
			try {
				Runtime runtime = Runtime.getRuntime();
				// Process process = runtime.exec(command, envp);
				Process process = runtime.exec(command);
				System.out.println(command);
				// 如js无法进行压缩打印命令报错信息
				BufferedInputStream bis = new BufferedInputStream(process.getErrorStream());
				BufferedReader br = new BufferedReader(new InputStreamReader(bis,"GB2312"));
				String line;
				while ((line = br.readLine()) != null) {
					System.out.println(line);
				}
				bis.close();
				br.close();
				if (process.waitFor() == 0) {
					count++;
				}
			} catch (Exception ex) {
				ex.printStackTrace();
			}
		}
		long endTime = System.currentTimeMillis();
		System.out.println("操作执行完成:共花费 " + (endTime - beginTime) + " ms, 共执行了 " + count + " 个文件");
	}

	private static List<String> initRmJsCommandList() throws Exception {
		List<String> cmdList = new ArrayList<>();
		for (String directionJ : CSS_JS_DIRECTION) {
			String lsCmd = "cmd /c dir/b " + PROJECT_PATH + "\\" +  RESOURCES_PATH + directionJ;
			Runtime runtime = Runtime.getRuntime();
			Process process = runtime.exec(lsCmd);
			if (process.waitFor() == 0) {
				InputStream inputStream = null;
				BufferedReader bufferedReader = null;
				try {
					inputStream = process.getInputStream();
					bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
					String line = null;
					while ((line = bufferedReader.readLine()) != null) {
						if (line.endsWith("-min.js") || line.endsWith("-min.css")) {
							StringBuilder stringBuilder = new StringBuilder();
							stringBuilder.append("cmd /c del").append(" ").append(" ").append(PROJECT_PATH).append("\\").append(RESOURCES_PATH).append(directionJ).append("\\").append(line);
							System.out.println("cmd:-->"+stringBuilder.toString());
							cmdList.add(stringBuilder.toString());
						}
					}
				} catch (Exception ex) {
					ex.printStackTrace();
				} finally {
					if (inputStream != null) {
						inputStream.close();
					}
					if (bufferedReader != null) {
						bufferedReader.close();
					}
				}
			}
		}

		return cmdList;
	}

	private static void replaceJsInHtml() throws Exception {
		for (String directionHtml : DIRECTION_HTML) {
			String absoluteDir = PROJECT_PATH + "\\" + RESOURCES_HTML_PATH + directionHtml;
			System.out.println("absoluteDir:--->"+absoluteDir);
			File htmlFile = new File(absoluteDir);
			File[] htmlFiles = htmlFile.listFiles();
			for (File hFile : htmlFiles) {
				BufferedReader bufferedReader = null;
				BufferedWriter bufferedWriter = null;
				try {
					String newFilePath = hFile.getAbsolutePath().substring(0, hFile.getAbsolutePath().indexOf(TEMP));
					bufferedReader = new BufferedReader(new InputStreamReader(new FileInputStream(hFile)));
					bufferedWriter = new BufferedWriter((new OutputStreamWriter(new FileOutputStream(new File(newFilePath)))));
					String line = null;
					while ((line = bufferedReader.readLine()) != null) {
						if (line.trim().contains("script") && line.trim().contains("src")) {
							Attribute srcAttribute = null;
							Document document = Jsoup.parse(line.trim());
							Iterator<Element> iterator = document.select("script").iterator();
							while (iterator.hasNext()) {
								Element next = iterator.next();
								Attributes attributes = next.attributes();
								for (Attribute attribute : attributes) {
									if ("src".equals(attribute.getKey())) {
										srcAttribute = attribute;
										break;
									}
								}
								break;
							}
							boolean w = false;
							if (srcAttribute != null) {
								for (String absolutePathName : RESOURCE_LIST) {
									if (!absolutePathName.trim().endsWith(".js")) {
										continue;
									}
									// 获取js路径上的上一级和js名称
									String[] split = absolutePathName.split("\\\\");
									String jsDirName = split[split.length - 2];
									String jsName = split[split.length - 1];
									String jsPreName = jsName.substring(0, jsName.indexOf(".js"));
									String[] srcSpilt = srcAttribute.getValue().split("\\/");
									String srcJsName = srcSpilt[srcSpilt.length - 1];
									String srcJsDirName = srcSpilt[srcSpilt.length - 2];
									if (!absolutePathName.contains("min.js") && jsDirName.equals(srcJsDirName) && srcJsName.contains(jsPreName)) {
										String newSrc = srcAttribute.getValue().substring(0, srcAttribute.getValue().indexOf(srcJsDirName + "/" + srcJsName));
										int startIndex = line.indexOf(jsDirName + "/" + jsPreName);
										int endIndex = line.indexOf(".js\"");
										String oldJsName = line.substring(startIndex, endIndex);
										String newLine = line.replace(oldJsName, jsDirName + "/" + jsPreName + "-" + DATE_STAMP + "-min");
										// 包含当前js文件,替换
										bufferedWriter.write(newLine + "\n");
										w = true;
									}
								}
							}
							if (!w) {
								bufferedWriter.write(line + "\n");
							}
						} else if (line.trim().contains("link") && line.trim().contains("href") && line.trim().contains("css")) {
							Attribute srcAttribute = null;
							Document document = Jsoup.parse(line.trim());
							Iterator<Element> iterator = document.select("link").iterator();
							while (iterator.hasNext()) {
								Element next = iterator.next();
								Attributes attributes = next.attributes();
								for (Attribute attribute : attributes) {
									if ("href".equals(attribute.getKey())) {
										srcAttribute = attribute;
										break;
									}
								}
								break;
							}
							boolean w = false;
							if (srcAttribute != null) {
								for (String absolutePathName : RESOURCE_LIST) {
									if (!absolutePathName.trim().endsWith(".css")) {
										continue;
									}
									// 获取css路径上的上一级和css名称
									String[] split = absolutePathName.split("\\\\");
									String cssDirName = split[split.length - 2];
									String cssName = split[split.length - 1];
									//System.out.println(cssName);
									String cssPreName = cssName.substring(0, cssName.indexOf(".css"));
									String[] srcSpilt = srcAttribute.getValue().split("\\/");
									String srcJsName = srcSpilt[srcSpilt.length - 1];
									String srcJsDirName = srcSpilt[srcSpilt.length - 2];
									if (!absolutePathName.contains("min.css") && cssDirName.equals(srcJsDirName) && srcJsName.contains(cssPreName)) {
										int startIndex = line.indexOf(cssDirName + "/" + cssPreName);
										int endIndex = line.indexOf(".css\"");
										String oldJsName = line.substring(startIndex, endIndex);
										String newLine = line.replace(oldJsName, cssDirName + "/" + cssPreName + "-" + DATE_STAMP + "-min");
										// 包含当前css文件,替换
										bufferedWriter.write(newLine + "\n");
										w = true;
									}
								}
							}
							if (!w) {
								bufferedWriter.write(line + "\n");
							}
						} else {
							bufferedWriter.write(line + "\n");
						}
						bufferedWriter.flush();
					}
				} catch (Exception ex) {
					ex.printStackTrace();
				} finally {
					if (null != bufferedReader) {
						bufferedReader.close();
					}
					if (null != bufferedWriter) {
						bufferedWriter.close();
					}
				}
			}
		}
	}

	private static void reverseReplaceJsInHtml() throws Exception {
		for (String directionHtml : DIRECTION_HTML) {
			String absoluteDir = PROJECT_PATH + "\\" + RESOURCES_HTML_PATH + directionHtml;
			File htmlFile = new File(absoluteDir);
			File[] htmlFiles = htmlFile.listFiles();
			for (File hFile : htmlFiles) {
				BufferedReader bufferedReader = null;
				BufferedWriter bufferedWriter = null;
				try {
					String newFilePath = hFile.getAbsolutePath().substring(0, hFile.getAbsolutePath().indexOf(TEMP));
					bufferedReader = new BufferedReader(new InputStreamReader(new FileInputStream(hFile)));
					bufferedWriter = new BufferedWriter((new OutputStreamWriter(new FileOutputStream(new File(newFilePath)))));
					String line = null;
					while ((line = bufferedReader.readLine()) != null) {
						String regex = "-[0-9]{13}-min";
						Pattern pattern = Pattern.compile(regex);
						Matcher matcher = pattern.matcher(line.trim());
						String datestamp_min_js = null;
						while (matcher.find()) {
							datestamp_min_js = matcher.group();
						}
						if(StringUtils.isNotBlank(datestamp_min_js)){
							String newLine = line.replace(datestamp_min_js, "");
							bufferedWriter.write(newLine + "\n");
						}else {
							bufferedWriter.write(line + "\n");
						}
						bufferedWriter.flush();
					}
				} catch (Exception ex) {
					ex.printStackTrace();
				} finally {
					if (null != bufferedReader) {
						bufferedReader.close();
					}
					if (null != bufferedWriter) {
						bufferedWriter.close();
					}
				}
			}
		}
	}

	/**
	 * 初始化压缩命令
	 *
	 * @param yuiPath
	 */
	private static List<String> initCommandList(String yuiPath) throws Exception {
		List<String> cmdList = new ArrayList<>();
		String[] cssOnly = {".css"};
		String[] thisSuffixArray = SUFFIXARRAY;
		if ("YES".equals(CSS_COMPRESS_ONLY)) {
			thisSuffixArray = cssOnly;
		}
		for (String directionJ : CSS_JS_DIRECTION) {
			String lsCmd = "cmd /c dir/b " + PROJECT_PATH + "\\" + RESOURCES_PATH + directionJ;
			Process process = Runtime.getRuntime().exec(lsCmd);
			InputStream inputStream = null;
			BufferedReader bufferedReader = null;
			if (process.waitFor() == 0) {
				inputStream = process.getInputStream();
				bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
				String line = null;
				while ((line = bufferedReader.readLine()) != null) {
					String suffix = line.substring(line.lastIndexOf("."));

					List<String> suffixList = Arrays.asList(thisSuffixArray);
					if (suffixList.contains(suffix) && !line.endsWith("-min" + suffix)) {
						StringBuffer sb = new StringBuffer();
						sb.append(" cmd /c");
						sb.append(" ");
						sb.append("java -jar ");
						sb.append(yuiPath);
						sb.append(" --type ");
						sb.append(suffix.substring(suffix.indexOf(".") + 1));
						sb.append(" --charset ");
						sb.append(encoding).append(" ");
						sb.append(" --preserve-semi ");
						StringBuffer _path = new StringBuffer();
						_path.append(PROJECT_PATH).append("\\");
						_path.append(RESOURCES_PATH).append(directionJ).append("\\").append(line).append(" ");
						RESOURCE_LIST.add(_path.toString());
						sb.append(_path);
						sb.append(">").append(" ");
						sb.append(PROJECT_PATH).append("\\");
						sb.append(RESOURCES_PATH).append(directionJ).append("\\").append(line.replace(suffix, "-" + DATE_STAMP + "-min" + suffix));
						cmdList.add(sb.toString());
					}
				}
			}
		}
		System.out.println("初始化压缩命令成功");
		return cmdList;
	}
}

如果遇到问题,可以debug看下是否配置了正确的执行路径、项目路径等,如果要压缩混淆的文件很少,也可以配置好上述内容后,执行如下命令

javascript-obfuscator D:\project\src\main\resources\static\js\login\login.js  --output D:\project\src\main\resources\static\js\login\login-1689667293081-min.js

这里login.js是我们要压缩混淆的文件,login-1689667293081-min.js是压缩混淆后的代码,挂上具体时间戳,然后,将其名称覆盖到对应的html页面即可

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/780678.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Vue第五篇:电商网站登录时vuex的使用

页面&#xff1a; 代码资源见&#xff1a;https://download.csdn.net/download/benben044/88071987 其中css使用开源库的UI&#xff0c;Main里面的元素是一张截图。 通过vuecli脚手架生成的代码架构如下&#xff1a; 一、入口组件App.vue解析 主页面主要由两部分组成&#x…

Leetcode-每日一题【114.二叉树展开为链表】

题目 给你二叉树的根结点 root &#xff0c;请你将它展开为一个单链表&#xff1a; 展开后的单链表应该同样使用 TreeNode &#xff0c;其中 right 子指针指向链表中下一个结点&#xff0c;而左子指针始终为 null 。 展开后的单链表应该与二叉树 先序遍历 顺序相同。 示例…

OSI七层模型和TCP/IP四层模型以及五层模型

OSI七层模型&#xff08;Open System Interconnect&#xff09;即开放系统互连参考模型&#xff0c;是由ISO&#xff08;International Organization for Standardization&#xff09;国际标准化组织提出的&#xff0c;用于计算机或通信系统间互联的标准体系。 从上到下可分为…

Flask 导航栏,模版渲染多页面

项目结构 app.py from flask import Flask, render_templateapp Flask(__name__)app.route(/) def index():return render_template(index.html)app.route(/secondpage) def secondpage():return render_template(secondpage.html)app.route(/threepage) def threepage():ret…

Linux驱动开发实战(一)——设备驱动模型

文章目录 前言设备驱动模型概述设备驱动模型的功能sysfs文件系统sysfs文件系统的目录结构 设备驱动模型的核心数据结构kobject结构体设备属性kobj_type 注册kobject到sysfs中的实例设备驱动模型结构kset集合kset与kobject的关系kset相关的操作函数注册kobject到sysfs中的实例实…

绘出「星辰大海」:华为云Astro轻应用新手指南-第一章

第1章 旅程的开端 发现Astro轻应用地图 第1站&#xff1a;创建账户 首先&#xff0c;你需要在华为云Astro官网注册专属账号。若已有华为账户&#xff0c;可直接登录。 在官网点击「立即使用」&#xff0c;即可跳转至「登录界面」 在「登录界面」点击「注册」&#xff0c;注册…

后端(四):博客系统项目

咱们在这里实现的是后端项目&#xff0c;前端代码就提一提&#xff0c;不全做重点介绍&#xff0c;在开始讲解这个博客系统项目之前&#xff0c;我们先看看这个项目的前端界面&#xff1a; 登录界面&#xff1a; 个人主页&#xff1a; 博客详情页&#xff1a; 写博客页&#x…

Python实战

官方文档 请点击下面工程名称&#xff0c;跳转到代码的仓库页面&#xff0c;将工程 下载下来 Demo Code 里有详细的注释 LearnPythonPython 实现功能点demo

Mac苹果系统安装双系统Windows10 Windows11 BOOTCAMP

Mac系统安装双系统Windows10 BOOTCAMP详细 1.下载Windows系统2.开始安装3.安装驱动4.默认启动5.备注 1.下载Windows系统 注意一下所有安装全程接充电器操作&#xff0c;以免安装过程中电脑断电带来不必要影响。 从下列方式选择合适的系统进行下载。 MSDN https://msdn.itelly…

【NLP】无服务器问答系统

一、说明 在NLP的眼见的应用&#xff0c;就是在“ 当你在谷歌上提出一个问题并立即得到答案时会发生什么&#xff1f;例如&#xff0c;如果我们在谷歌搜索中询问谁是美国总统&#xff0c;我们会得到以下回答&#xff1a;Joe Biden&#xff1b;这是一个搜索问题&#xff0c;同时…

概率论的学习和整理--番外14:如何理解 dutu输光定理

解决问题 1 dutu 拿100是赌一次好&#xff0c;还是100次1元的好&#xff1f; 一般的地方&#xff0c;如果不是公平赌局&#xff0c;而期望是负数的话 其实du次数越多越亏 2 1%就基本能决定胜负 了 3 千万不要陷入常人思维&#xff0c;用筹码数量思考&#xff0c;输光为止&am…

选读SQL经典实例笔记10_高级查询

1. 结果集分页 1.1. 只有做过了排序&#xff0c;才有可能准确地从结果集中返回指定区间的记录 1.2. DB2 1.3. Oracle 1.4. SQL Server 1.5. sql select salfrom ( select row_number() over (order by sal) as rn,salfrom emp) xwhere rn between 1 and 5 SAL ----800 95…

周末作业 c++

将顺序栈&#xff0c;循环队列定义成模板类型&#xff1a; #include <iostream>using namespace std;template <typename T,int Maxsize> class seqstack { private:T data[Maxsize];int top; public:seqstack() //无参构造{top-1;cout<<"无参构造…

jenkins使用企业微信进行审批

该篇文章实现了基于企业微信进行审批的功能&#xff08;也支持其他的webhook&#xff09; 前提是进行sharelibrary的配置 一、首先我们使用jenkins的sharelibrary进行审批人全局参数的设置&#xff08;该步骤是为了当审批人变动时不需要该每个pipeline只改动全局变量即可&…

❤️创意网页:抖音汉字鬼抓人小游戏复刻——附带外挂(“鬼鬼定身术”和“鬼鬼消失术”)坚持60秒轻轻松松(●‘◡‘●)

✨博主&#xff1a;命运之光 &#x1f338;专栏&#xff1a;Python星辰秘典 &#x1f433;专栏&#xff1a;web开发&#xff08;简单好用又好看&#xff09; ❤️专栏&#xff1a;Java经典程序设计 ☀️博主的其他文章&#xff1a;点击进入博主的主页 前言&#xff1a;欢迎踏入…

《零基础入门学习Python》第053讲:论一只爬虫的自我修养

0. 请写下这一节课你学习到的内容&#xff1a;格式不限&#xff0c;回忆并复述是加强记忆的好方式&#xff01; 马上我们的教学就要进入最后一个章节&#xff0c;Pygame 嗨爆引爆全场&#xff0c;但由于发生了一个小插曲&#xff0c;所以这里决定追加一个章节&#xff0c;因为…

下载|GitLab 2023 年 DevSecOps 全球调研报告:安全左移深入人心、AI/ML 蔚然成风

目录 谁应该对应用程序安全负主要责任&#xff1f; 安全实践的最大挑战 AI 驱动研发&#xff0c;提升研发效率 各个角色使用的工具数量是多少&#xff1f; 一体化 DevSecOps 平台有哪些优势&#xff1f; 56%、74%、71%、65%、57% 这些数字和 DevSecOps 结合在一起&#xf…

Java -- 元注解

元注解 就是 Java标准库中 原生的注解&#xff0c;有点类似于 Java类 中的 Object&#xff0c;由于添加在其他注解上 Java总共有四个元注解&#xff0c;他们的功能如下&#xff1a; Target(ElementType.ANNOTATION_TYPE)&#xff1a;指定该注解可以用于注解类、接口或枚举类型…

element 表格里,每一行都循环使用el-popover组件,关闭按钮失效问题如何解决?

具体代码 <!DOCTYPE html> <html lang"zh"><head><meta charset"UTF-8"><title></title><link rel"stylesheet" href"https://unpkg.com/element-ui/lib/theme-chalk/index.css"><styl…

Linux Misc 驱动-编写驱动例程基于iTOP-STM32P157开发板

首先我们回想一下注册杂项设备的三大流程&#xff0c;我们在 Windows 上面新建 misc.c 文件&#xff0c;并用 sourceinsight 打开。我们可以将上次编写的 helloworld.c 里面的代码拷贝到 misc.c 文件&#xff0c;并修改为如下图所示 添加头文件 /*注册杂项设备头文件*/ #inc…