再见word,Node.js批量生成的艺术
在信息系统没有完善的地方,数据要汇总EXCEL中,如果分发给每个学生填入Word,必然浪费众人的N分钟。
根据每个人提交的Word文档打印,那么格式调整是灾难。 不同的系统,不同的Word版本,再碰上图片围绕带来的浮动错乱,一天就尽整格式了!
上学时,老师喜欢说,因为某个同学讲话耽误全班所有人的2分钟。 工作了,因为信息化系统落后,让每个人在Word中填信息打印,将浪费所有人的2分钟。
Node.js驱动word,只关心数据忽略格式,避免人人都要浪费时间在编辑Word文档。
一、目标Word模版
为了便于快速理解,简化了目标表格如下。
二、解决方案
- 方案一:办公软件的邮件合并功能,缺陷是主要针对文本,对于判断条件和多选不容易操作。
- 方案二: 主要使用Node.js第三方模块
docxtemplater
进行docx类型文档插值。有更好的灵活性、自由度。
相比word、excel里面受限,程序员为了freeeeeedoooom当然选择Node.js编程。
主要思路:构造Word模版、确定数据结构、循环生成word。
第一步、构造Word模版
就是在Word文件中挖空,可以看出docxtemplater
模版插值语法使用{变量名}
的形式插值,
遍历数组使用{#数组}{.}{/数组}
进行,其中{.}
代表每个数组元素
第二步、确定数据结构
单个同学的数据结构如下:
2.1 ☑多选打√的问题
除了√还需要解决文本对齐问题。这里使用两个函数。根据数组下标来打☑,然后选一个 最长的长度,来设置同样的宽度,宽度不够空格来凑,这里注意处理中文字符=2个空格的问题。 小技巧:必要时可以用鼠标拉大最外层宽度。
function 设置重点类型人群(数据) {
let arr = 数据.重点群体;
for (let i = 0; i < 数据.z.length; i++) { //实现长度对齐
let v = `□`
let one = 数据.z[i];
let len = L(one)
let s = ''
for (let j = 0; j < 18 - len; j++) {
s += ' '
}
if (arr.includes(i)) {
v = '☑'
}
数据.z[i] = `${one}${v}${s}`
console.dir(数据.z[i])
}
}
function L(str) {
let length = 0;
for (let i = 0; i < str.length; i++) {
// 如果字符的charCodeAt大于255,我们假设它是中文字符或其他双字节字符
if (str.charCodeAt(i) > 255) {
length += 2;
} else {
length += 1;
}
}
return length;
}
function 设置就业意向(数据){
const arr = ["单位就业", "自主创业", "自由职业", "升学", "待就业", "暂不就业"]
let n = arr.indexOf(数据.就业意向)
for(let i =0 ; i< 数据.j.length;i++){
let v = `□`
let one = 数据.j[i];
//let len = L(one)
if( n == i ){
v = '☑'
}
数据.j[i] = `${one}${v} ` //默认3个空格
}
}//设置就业意向
第三步 循环生成word
根据需要将以下代码封装,循环给 数据赋值。
从EXCEL中获取数据 ,使用 exceljs
模块。
const PizZip = require("pizzip"); // 引入PizZip模块
const Docxtemplater = require("docxtemplater"); // 引入Docxtemplater模块
const fs = require("fs");
const path = require("path");
// 增加循环 和代码 封装
let 数据 ={ }
设置重点类型人群(数据)
设置就业意向(数据)
const content = fs.readFileSync("附件3.docx", "binary");
// 解压文件的内容
const zip = new PizZip(content); // 创建一个新的PizZip实例
// 解析模板,并在模板无效时抛出错误,例如,如果模板是"{user"(没有闭合标签)
const doc = new Docxtemplater(zip, { // 创建Docxtemplater实例
paragraphLoop: true, // 允许段落循环
linebreaks: true, // 保持换行符
});
doc.render(数据);
// 获取zip文档并将其生成为Node.js缓冲区
const buf = doc.getZip().generate({ // 生成文档的zip格式
type: "nodebuffer", // 生成类型为nodebuffer
compression: "DEFLATE", // 压缩类型为DEFLATE
});
fs.writeFileSync("附件3生成.docx", buf); // 将渲染后的文档写入到output.docx文件
三、注意事项
1.提前准备好Word模版,演示可以在word中设置,而不通过程序 2.先测试好单个数据源,再测试批量数据 3.编程的解决方案通常是超越软件本身的
四、参考文献:
docxtemplater.com/docs/get-st…
转载自:https://juejin.cn/post/7393313322210312227