NodeJs实现脚本:将xlxs文件输出到json文件中

文章目录

    • 前期工作和依赖
    • 笔记
    • 功能
    • 代码
    • 输出

最近有一个功能,将json文件里的内容抽取到一个xlxs中,然后维护xlxs文件。当要更新json文件时,就更新xlxs的内容并把它传回json中。这个脚本主要使用NodeJS写。

以下是完成此功能时做的一些笔记。

前期工作和依赖

js文件中要使用import,因此需要在package.json中设置:"type": "module"

依赖:

import xlsx from 'xlsx';
import path, { dirname } from 'node:path';
import fs from 'node:fs';
import { fileURLToPath } from 'node:url';
import md5 from 'blueimp-md5';

相关文档:
API 参考 | SheetJS 中文网 (nodejs.cn)
xlsx - npm (npmjs.com)

笔记

获取此文件目录名:

const __dirname = dirname(fileURLToPath(import.meta.url));

组合文件名:

const outPath = path.join(__dirname, './fileName.xlsx');

读取一个目录下的所有文件名:

const files = fs.readdirSync(dirName);

读取一个文件:

const enJson = fs.readFileSync(fileName, 'utf8');

将二维数组转换为xlxs工作表:

const sheet = xlsx.utils.aoa_to_sheet(sheetData);

将工作表添加到工作簿:

xlsx.utils.book_append_sheet(workBook, sheet, sheetName);

将工作表输出到xlsx文件中:

xlsx.writeFile(workBook, outPath, { bookType: 'xlsx' });

将数组输出到xlxs:data是数组。

const sheet = xlsx.utils.json_to_sheet(data); //将 JS 对象数组转换为工作表
const workBook= xlsx.utils.book_new();// 创建一个工作簿对象
xlsx.utils.book_append_sheet(workBook, sheet, 'sheetName'); // 将工作表添加到工作簿:
xlsx.writeFile(workBook, path, {bookType: 'xlsx',
}); // 输出到xlsx

功能

维护一个xlsx文档,里面包含国际化的所有翻译,如下:第一行 为 语言

enkojafr
英文翻译韩文翻译日文翻译法文翻译

有英文json翻译文件如下:src/locales/en/fileName1.json

其中key值为i18n的标记,value值为对应的翻译。

{"inviter": "Inviter","worth": "Worth ${{value}}","countDownTips": "Rewards Countdown"
}

默认语言为英语,我们需要以它为例子生成对应的其他语言文件,如生成:src/locales/fr/fileName1.json

{"inviter": "法文翻译1","worth": "法文翻译2","countDownTips": "法文翻译3"
}

所有的翻译都在xlsx中。因此我们需要读取xlsx文件,遍历src/locales/en下的对应文件(参数pageNames),将对应翻译生成到对应文件夹。若无对应翻译,则用英文兜底。

中途使用md5加密后的en翻译为key,将对应xlsx文件中的翻译(那一行)保存到set中,是因为xlsx中没有i18n标记,只有各语言翻译

将xlsx翻译文件输出到locales/[language]/[fileName]的功能封装成一个函数,参数如下:

读入的en文件夹上级为pagePath
参数:
pageNames:要维护的文件名列表,如 invite 对应locale/en/invite
filePath:xlsx文件路径
pagePath:locale文件路径
option:选项,包括
- outputKey:输出为json的某一个key值的value,没有就不填 (这个功能的代码很死板,像是硬编码,需求如此,先写着!)
- languageArray:传入一个数组,包含要求的语言,没有就不填,会默认xlsx里的所有文件

参数填错了就会报错,这个代码的健壮性并不强,只是一个加快工作效率的工具 / 练手代码。 所以建议严格按照参数要求调用函数。不要做那种:“没有outputKey应该不传,但我就传个空串”,可能会报奇怪的错误!

代码

// 入口
import xlsx from "xlsx";
import md5 from "blueimp-md5";
import fs from "node:fs";
import path from "node:path";// 删去前后空格 特判str为undefined
const trim = (str) => (str || "").replace(/^\s+|\s+$/g, "");// 生成一个set,key是en的翻译,value是对应row
function transSheetToMap(sheetData) {const map = new Map();for (const row of sheetData) {const key = md5(trim(row.en));map.set(key, row); // 加密后en的value为key,整个row为value}return map;
}/*
读入的en文件夹上级为pagePathpageNames:要维护的文件名列表,如 invite 对应locale/en/invite 
filePath:xlsx文件路径
pagePath:locale文件路径
option:选项,包括- outputKey:输出为json的某一个key值的value,没有就不填- languageArray:传入一个数组,包含要求的语言缩写,没有就不填,会默认xlsx里的所有文件
*/
function xlsxToJson(pageNames, filePath, pagePath, option) {let outputKey = undefined;if (option.outputKey) {outputKey = option.outputKey;}const workBook = xlsx.readFile(filePath);const firstWorksheet = workBook.SheetNames[0]; // 全都放在第一个sheet中const sheet = workBook.Sheets[firstWorksheet];const sheetData = xlsx.utils.sheet_to_json(sheet); // 数组,每个项是对象,key为语言value为翻译const languages = option.languageArray? option.languageArray: Object.keys(sheetData[0]); // 所有语言const dictions = transSheetToMap(sheetData);for (const pageName of pageNames) {// 英文文件const pageEnJson = JSON.parse(fs.readFileSync(path.join(pagePath, "en", `${pageName}.json`),"utf8"));// key 为 i18n标记const pageEnKeys = outputKey? Object.keys(pageEnJson[outputKey]): Object.keys(pageEnJson);for (const language of languages) {// 深拷贝英文样本const translatedJson = JSON.parse(JSON.stringify(pageEnJson));// translatedJson生成为对应语言,en兜底for (const key of pageEnKeys) {const translatedKey = outputKey? md5(trim(pageEnJson[outputKey][key])): md5(trim(pageEnJson[key]));const translation = dictions.get(translatedKey);if (outputKey) {translatedJson[outputKey][key] =translation[language] || translation["en"];} else {translatedJson[key] =translation[language] || translation["en"];}}const filePath = path.join(pagePath, language, `${pageName}.json`);// 若文件夹不存在则创建if (!fs.existsSync(path.join(pagePath, language))) {fs.mkdirSync(path.join(pagePath, language));}fs.writeFileSync(filePath, JSON.stringify(translatedJson, null, 4));}}
}export default xlsxToJson;
xlsxToJson(["invite", "player"],"C:/Users/somePath/i18n-all.xlsx","C:/Users/somePath/locales",{outputKey: "key",languageArray: ["de"],}
);

输出

调用:要翻译的文件为invite,输出到json文件的key属性中,只翻译到de德文。

xlsxToJson(["invite"],"C:/Users/somePath/i18n-all.xlsx","C:/Users/somePath/locales",{outputKey: "key",languageArray: ["de"],}
);

对应英文json如下:(有outputKey一定要填!没有的话一定不填!不然输出会很奇怪。)

// locales/en/invite.json
{"key": {"ogDesc": "Download Now!","inviter": "Inviter"}
}

结果输出locales/de/invite.json

在这里插入图片描述

可能会封装一个npm包,可能会维护。笔记先写在这吧!

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

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

相关文章

【面试八股总结】内存页面置换算法

参考资料:小林coding、阿秀 缺页中断 在 CPU 里访问一条 Load M 指令,然后 CPU 会去找 M 所对应的页表项。如果该页表项的状态位是「有效的」,那 CPU 就可以直接去访问物理内存了,如果状态位是「无效的」,则 CPU 则会…

stanfordcorenlp+python做中文nlp任务,得到的结果中全是空字符串,而不是中文字符串

问题描述 代码: from stanfordcorenlp import StanfordCoreNLP import logging#中文中的应用,一定记得下载中文jar包,并标志lang‘zh’ nlp_zh StanfordCoreNLP(rD:\stanford-corenlp-full-2016-10-31, port8094, langzh,quietFalse,logg…

GiantPandaCV | 提升分类模型acc(一):BatchSizeLARS

本文来源公众号“GiantPandaCV”,仅用于学术分享,侵权删,干货满满。 原文链接:提升分类模型acc(一):BatchSize&LARS 在使用大的bs训练情况下,会对精度有一定程度的损失,本文探讨了训练的b…

Java Web学习笔记24——Vue项目开发流程

import是引入文件。 export是将对象导出为模块。 new Vue({ router, router: h > h(App) }).$mount(#app) App.vue: vue的组成文件以.vue结尾&#xff0c;每个组件由三个部分组成&#xff1a;<template>、<script>、<style>。 <template><d…

i.MX8MP平台开发分享(RDC软件配置篇)

Uboot中已经将RDC的配置写入到了OCRAM中&#xff0c;NXP在ATF中预设了SIP服务&#xff0c;SIP服务下有厂商自定义的smc命令ID。例如下面的DDR、GPC、SRC和HAB的smc回调函数。 在SRC中断处理函数中&#xff0c;对于SRC_M4_START指令&#xff0c;先读取OCRAM中的配置&#xff0c;…

第一个小爬虫_爬取 股票数据

前言 爬取 雪球网的股票数据 [环境使用]&#xff1a;python 3.12 解释器pycharm 编辑器 【模块使用】&#xff1a;import requests -->数据请求模块 要安装 命令 pip install requestsimport csv -->将数据保存到CSV表格中import pandas -->也可以将数据保…

vue3+vite插件开发

插件开发目的:由于我司使用的前端技术栈为vue3tsvite2.Xaxios,在前端代码框架设计初期,做了把axios挂载到proxy对象上的操作,具体可见我的另一篇文章vue3TS自动化封装全局api_ts 封装腾讯位置api-CSDN博客 现在可以实现vue2的类似this.$api.xxx去调用接口,但是vue2源码使用的是…

flutter日历范围选择器

1.传入日期跨度&#xff0c;选择上架日期时&#xff0c;自动显示下架日期 2.手动选择上架日期和下架日期(图中下架日期自动填了只需CalendarDateRangePicker在initState方法中使用_startDate widget.initialStartDate; _endDate widget.initialEndDate;&#xff0c;而不直接…

【python】OpenCV—Blob Detection(11)

学习来自OpenCV基础&#xff08;10&#xff09;使用OpenCV进行Blob检测 文章目录 1、cv2.SimpleBlobDetector_create 中文文档2、默认 parameters3、配置 parameters附录——cv2.drawKeypoints 1、cv2.SimpleBlobDetector_create 中文文档 cv2.SimpleBlobDetector_create 是 O…

端午搞个零花钱,轻松赚取创业的第一桶金!2024最受欢迎的创业项目,2024新的创业机会

好好的端午节&#xff0c; 净给我添堵&#xff01; 本来我打算在端午节愉快的玩耍&#xff0c; 结果一大早起床却看到舍友在给一堆设备充电&#xff0c; 然后装的整整齐齐&#xff0c; 满满一书包。 我好奇他小子这是要干嘛&#xff1f; 不会是打算今天回去给亲朋好友准备…

【动态规划-BM79 打家劫舍(二)】

题目 BM79 打家劫舍(二) 描述 你是一个经验丰富的小偷&#xff0c;准备偷沿湖的一排房间&#xff0c;每个房间都存有一定的现金&#xff0c;为了防止被发现&#xff0c;你不能偷相邻的两家&#xff0c;即&#xff0c;如果偷了第一家&#xff0c;就不能再偷第二家&#xff0c;如…

全面分析找不到msvcr120.dll,无法继续执行程序问题

在计算机使用过程中&#xff0c;我们可能会遇到一些错误提示&#xff0c;其中“找不到msvcr120.dll”就是常见的一种。那么&#xff0c;找不到msvcr120.dll是什么意思呢&#xff1f; 一&#xff0c;msvcr120.dll文件概述 msvcr120.dll 是 Microsoft Visual C Redistributable …

C++教程(003):运算符

3 运算符 作用&#xff1a;用于执行代码的运算 我们主要讲解以下运算符&#xff1a; 运算符类型作用算术运算符用于处理四则运算赋值运算符用于将表达式的值赋给变量比较运算符用于表达式的比较&#xff0c;并返回一个真值或假值逻辑运算符用于根据表达式的值返回真值或假值 …

详解 Flink 的时间语义和 watermark

一、Flink 时间语义类型 Event Time&#xff1a;是事件创建的时间。它通常由事件中的时间戳描述&#xff0c;例如采集的日志数据中&#xff0c;每一条日志都会记录自己的生成时间&#xff0c;Flink 通过时间戳分配器访问事件时间戳Ingestion Time &#xff1a;是数据进入 Flink…

el-table合计行前置在首行,自定义合计行方法

背景 el-table原生合计行是在标签内增加show-summary属性&#xff0c;在表尾实现设计合计&#xff0c;且只对表格当前页面显示的列数据进行合计。element-UI效果如下图所示。 现要求在首行显示合计行&#xff0c;并自定义合计逻辑实现如下效果。 图示表格中&#xff0c;成本…

【渗透测试】DC-1靶机实战(上)漏洞扫描获取反弹shell

目录 一、范围界定 二、信息收集 三、目标识别 1&#xff09;主机发现 2&#xff09;端口扫描 四. 服务枚举 1&#xff09;网站首页 2&#xff09;Web指纹识别 3&#xff09;nikto报告 4&#xff09;robots.txt 5&#xff09;UPGRADE.txt 五. 漏洞映射 1&#xff…

万字长文|OpenAI模型规范(全文)

本文是继《OpenAI模型规范概览》之后对OpenAI Model Spec的详细描述&#xff0c;希望能对各位从事大模型及RLHF研究的朋友有帮助。万字长文&#xff0c;建议收藏后阅读。 一、概述 在AI的世界里&#xff0c;确保技术的行为符合我们的期望至关重要。OpenAI最近发布了一份名为Mo…

今天是放假带娃的一天

端午节放假第一天 早上5点半宝宝就咔咔乱叫了&#xff0c;几乎每天都这个点醒&#xff0c;准时的很&#xff0c;估计他是个勤奋的娃吧&#xff0c;要早起锻炼婴语&#xff0c;哈哈 醒来后做饭、洗锅、洗宝宝的衣服、给他吃D3&#xff0c;喂200ml奶粉、给他洗澡、哄睡&#xff0…

代码随想录算法训练营第二十二天

题目&#xff1a;216. 组合总和 III 这道题和上道题非常类似&#xff0c;大体框架一样只不过修改一下终止条件而已 值得注意的是其中的剪枝条件的设置 一是靠现有的元素和已经大于目标和的话就提前终止&#xff0c;另一个是其中循环那个剪枝可以记住 i < n - (k - path.s…

YOLOv8改进 | 卷积模块 | 在主干网络中添加/替换蛇形卷积Dynamic Snake Convolution

&#x1f4a1;&#x1f4a1;&#x1f4a1;本专栏所有程序均经过测试&#xff0c;可成功执行&#x1f4a1;&#x1f4a1;&#x1f4a1; 蛇形动态卷积是一种新型的卷积操作&#xff0c;旨在提高对细长和弯曲的管状结构的特征提取能力。它通过自适应地调整卷积核的权重&#xff0…