xml-disassembler
Version:
Disassemble XML files into smaller, more manageable files and reassemble the XML when needed.
3 lines (2 loc) • 11.3 kB
JavaScript
!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("log4js"),require("node:fs/promises"),require("node:path/posix"),require("yaml"),require("json5"),require("smol-toml"),require("ini"),require("node:fs"),require("node:path"),require("ignore"),require("node:crypto"),require("fast-xml-parser")):"function"==typeof define&&define.amd?define(["exports","log4js","node:fs/promises","node:path/posix","yaml","json5","smol-toml","ini","node:fs","node:path","ignore","node:crypto","fast-xml-parser"],t):t((e="undefined"!=typeof globalThis?globalThis:e||self).jsTemplate={},e.log4js,e.promises,e.posix,e.yaml,e.json5,e.smolToml,e.ini,e.node_fs,e.node_path,e.ignore,e.node_crypto,e.fastXmlParser)}(this,(function(e,t,n,i,r,s,o,l,d,a,c,u,f){"use strict";function m(e,t,n,i){return new(n||(n=Promise))((function(r,s){function o(e){try{d(i.next(e))}catch(e){s(e)}}function l(e){try{d(i.throw(e))}catch(e){s(e)}}function d(e){var t;e.done?r(e.value):(t=e.value,t instanceof n?t:new n((function(e){e(t)}))).then(o,l)}d((i=i.apply(e,t||[])).next())}))}"function"==typeof SuppressedError&&SuppressedError;const p=" ",y={commentPropName:"!---",ignoreAttributes:!1,ignoreNameSpace:!1,parseTagValue:!1,parseNodeValue:!1,parseAttributeValue:!1,trimValues:!0,processEntities:!1,cdataPropName:"![CDATA["},h=Object.assign(Object.assign({},y),{format:!0,indentBy:p,suppressBooleanAttributes:!1,suppressEmptyNode:!1});function g(e,t=0){return new f.XMLBuilder(h).build(e).split("\n").map((e=>`${" ".repeat(4*t)}${e}`)).join("\n").trimEnd()}function $(e){return m(this,void 0,void 0,(function*(){const t=new f.XMLParser(y),i=yield n.readFile(e,"utf-8");let r;try{return r=t.parse(i,!0),r}catch(t){return void W.error(`${e} was unabled to be parsed and will not be processed. Confirm formatting and try again.`)}}))}function b(e,t){let n=`<${t}`;for(const[t,i]of Object.entries(e))if(t.startsWith("@")){n+=` ${t.slice(2)}="${String(i)}"`}return n+=">",n}function v(e){let t='<?xml version="1.0" encoding="UTF-8"?>';if(e["?xml"]){const n=e["?xml"];t=`<?xml ${Object.entries(n).map((([e,t])=>`${e.replace("@_","")}="${t}"`)).join(" ")}?>`}return t}function j(e){return m(this,void 0,void 0,(function*(){const t=v(e),n=Object.keys(e)[1];return[n,b(e[n],n),t]}))}function x(e,t){if(void 0===t)return E(e);const n=t.split(",");for(const t of n)if(void 0!==e[t]&&"string"==typeof e[t])return e[t];for(const n in e)if("object"==typeof e[n]&&null!==e[n]){const i=x(e[n],t);if(void 0!==i)return i}return E(e)}function E(e){const t=u.createHash("sha256");t.update(JSON.stringify(e));return t.digest("hex").slice(0,8)}function P(e){return m(this,void 0,void 0,(function*(){const t=yield $(e),i=r.stringify(t),s=e.replace(/\.xml$/,".yaml");yield n.writeFile(s,i),W.debug(`${e} has been transformed into ${s}`)}))}function w(e){return m(this,void 0,void 0,(function*(){const t=yield $(e),i=s.stringify(t,null,2),r=e.replace(/\.xml$/,".json5");yield n.writeFile(r,i),W.debug(`${e} has been transformed into ${r}`)}))}function C(e){return m(this,void 0,void 0,(function*(){const t=yield $(e),i=JSON.stringify(t,null,2),r=e.replace(/\.xml$/,".json");yield n.writeFile(r,i),W.debug(`${e} has been transformed into ${r}`)}))}function F(e){return m(this,void 0,void 0,(function*(){const t=yield $(e),i=o.stringify(t),r=e.replace(/\.xml$/,".toml");yield n.writeFile(r,i),W.debug(`${e} has been transformed into ${r}`)}))}function q(e){return m(this,void 0,void 0,(function*(){const t=yield $(e),i=l.stringify(t),r=e.replace(/\.xml$/,".ini");yield n.writeFile(r,i),W.debug(`${e} has been transformed into ${r}`)}))}function N(e){switch(e){case"yaml":return P;case"json5":return w;case"json":return C;case"toml":return F;case"ini":return q;default:return}}function O(e,t,r,s,o,l,d,a,c){return m(this,void 0,void 0,(function*(){let u="";const f=x(e,r),m=i.join(t,l),p=`${f}.${l}-meta.xml`,y=i.join(m,p);yield n.mkdir(m,{recursive:!0});const h=b(e,l);u=g(e,2);let $=`${a}\n`;$+=`${o}\n`,$+=`${d}${h}\n`,$+=`${u}\n`,$+=`${d}</${l}>\n`,$+=`</${s}>`,yield n.writeFile(y,$),W.debug(`Created disassembled file: ${y}`);const v=N(c);v&&(yield v(y),yield n.rm(y))}))}function S(e){return m(this,void 0,void 0,(function*(){const{element:t,disassembledPath:n,uniqueIdElements:i,rootElementName:r,rootElementHeader:s,key:o,indent:l,leafContent:d,leafCount:a,hasNestedElements:c,xmlDeclarationStr:u,format:f}=e;if("object"==typeof t)return yield O(t,n,i,r,s,o,l,u,f),[d,a,!0];return[`${d}${l}<${o}>${String(t)}</${o}>\n`,a+1,c]}))}function T(e,t,r,s,o,l,d){return m(this,void 0,void 0,(function*(){let a=`${l}\n`;a+=`${o}\n`,a+=e,a+=`</${s}>`;const c=i.join(t,`${r}.xml`);yield n.writeFile(c,a),W.debug(`Created disassembled file: ${c}`);const u=N(d);u&&(yield u(c),yield n.rm(c))}))}function L(e){return m(this,void 0,void 0,(function*(){const{element:t,key:n,indent:i,leafContent:r,leafCount:s,hasNestedElements:o}=e,l={};if("object"==typeof t)return l[n]||(l[n]=[]),l[n].push(t),{leafContent:r,leafCount:s,hasNestedElements:!0,nestedGroups:l};return{leafContent:`${r}${i}<${n}>${String(t)}</${n}>\n`,leafCount:s+1,hasNestedElements:o,nestedGroups:l}}))}function k(e,t,r,s,o,l,d,a){return m(this,void 0,void 0,(function*(){const c=i.join(r,`${e}.xml`);yield n.mkdir(r,{recursive:!0});let u=`${l}\n${o}\n`;for(const n of t){const t=Object.entries(n).filter((([e,t])=>A(e,t))).map((([e,t])=>` ${e.replace(/^@_/,"")}="${t}"`)).join(""),i=Object.fromEntries(Object.entries(n).filter((([e])=>!e.startsWith("@_"))));u+=`${d}<${e}${t}>\n`,u+=g(i,2),u+=`\n${d}</${e}>\n`}u+=`</${s}>`,yield n.writeFile(c,u),W.debug(`Created grouped nested file: ${c}`);const f=N(a);f&&(yield f(c),yield n.rm(c))}))}function A(e,t){return e.startsWith("@_")&&("string"==typeof t||"number"==typeof t)}const W=t.getLogger();t.configure({appenders:{disassemble:{type:"file",filename:"disassemble.log"}},categories:{default:{appenders:["disassemble"],level:"error"}}}),e.DisassembleXMLFileHandler=class{constructor(){this.ign=c()}disassemble(e){return m(this,void 0,void 0,(function*(){const{filePath:t,uniqueIdElements:i,strategy:r="unique-id",prePurge:s=!1,postPurge:o=!1,ignorePath:l=".xmldisassemblerignore",format:c="xml"}=e,u=a.resolve(l);if(d.existsSync(u)){const e=yield n.readFile(u);this.ign.add(e.toString())}const f=yield n.stat(t),m=this.posixPath(a.relative(process.cwd(),t));if(f.isFile()){const e=a.resolve(t);if(!e.endsWith(".xml"))return void W.error(`The file path provided is not an XML file: ${e}`);if(this.ign.ignores(m))return void W.warn(`File ignored by ${l}: ${e}`);const n=a.dirname(e);yield this.processFile({dirPath:n,strategy:r,filePath:e,uniqueIdElements:i,prePurge:s,postPurge:o,format:c})}else if(f.isDirectory()){const e=yield n.readdir(t);for(const n of e){const e=a.join(t,n),d=this.posixPath(a.relative(process.cwd(),e));e.endsWith(".xml")&&!this.ign.ignores(d)?yield this.processFile({dirPath:t,strategy:r,filePath:e,uniqueIdElements:i,prePurge:s,postPurge:o,format:c}):this.ign.ignores(d)&&W.warn(`File ignored by ${l}: ${e}`)}}}))}processFile(e){return m(this,void 0,void 0,(function*(){const{dirPath:t,strategy:i,filePath:r,uniqueIdElements:s,prePurge:o,postPurge:l,format:c}=e;W.debug(`Parsing file to disassemble: ${r}`);const u=a.basename(r,a.extname(r)),f=u.split(".")[0];let y;y=a.join(t,f),o&&d.existsSync(y)&&(yield n.rm(y,{recursive:!0})),"grouped-by-tag"===i?yield function(e,t,i,r,s,o){return m(this,void 0,void 0,(function*(){const l=yield $(e);if(void 0===l)return;const d=Object.keys(l)[1],a=v(l),c=l[d],u=b(c,d);let f="",m=0,p=!1;const y={};for(const e of Object.keys(c).filter((e=>!e.startsWith("@")))){const t=Array.isArray(c[e])?c[e]:[c[e]];for(const n of t){const t=yield L({element:n,key:e,indent:r,leafContent:f,leafCount:m,hasNestedElements:p});f=t.leafContent,m=t.leafCount,p=t.hasNestedElements;for(const e in t.nestedGroups)y[e]||(y[e]=[]),y[e].push(...t.nestedGroups[e])}}if(p){for(const e in y)yield k(e,y[e],t,d,u,a,r,o);m>0&&(yield T(f,t,i,d,u,a,o)),s&&(yield n.unlink(e))}else W.error(`The XML file ${e} only has leaf elements. This file will not be disassembled.`)}))}(r,y,u,p,l,c):yield function(e,t,i,r,s,o,l){return m(this,void 0,void 0,(function*(){const d=yield $(e);if(void 0===d)return;const a=Object.keys(d)[1],c=v(d),u=d[a],f=b(u,a);let m="",p=0,y=!1;for(const e of Object.keys(u).filter((e=>!e.startsWith("@"))))if(Array.isArray(u[e]))for(const n of u[e]){const[r,o,d]=yield S({element:n,disassembledPath:t,uniqueIdElements:i,rootElementName:a,rootElementHeader:f,key:e,indent:s,leafContent:m,leafCount:p,hasNestedElements:y,xmlDeclarationStr:c,format:l});m=r,p=o,y=d}else{const[n,r,o]=yield S({element:u[e],disassembledPath:t,uniqueIdElements:i,rootElementName:a,rootElementHeader:f,key:e,indent:s,leafContent:m,leafCount:p,hasNestedElements:y,xmlDeclarationStr:c,format:l});m=n,p=r,y=o}y?(p>0&&(yield T(m,t,r,a,f,c,l)),o&&n.unlink(e)):W.error(`The XML file ${e} only has leaf elements. This file will not be disassembled.`)}))}(r,y,s,u,p,l,c)}))}posixPath(e){return e.replace(/\\+/g,"/")}},e.ReassembleXMLFileHandler=class{processFilesInDirectory(e){return m(this,void 0,void 0,(function*(){const t=[];let r;const s=yield n.readdir(e);s.sort(((e,t)=>{const n=e.split(".")[0].toLowerCase(),i=t.split(".")[0].toLowerCase();return n.localeCompare(i)}));for(const o of s){const s=i.join(e,o),l=yield n.stat(s);if(l.isFile()){if(/\.(xml|json|json5|ya?ml|toml|ini)$/.test(o)){const e=yield this.parseToXmlObject(s);if(void 0===e)continue;r=yield j(e);const n=g(e);t.push(n)}}else if(l.isDirectory()){const[e,n]=yield this.processFilesInDirectory(s);t.push(...e),r=n}}return[t,r]}))}reassemble(e){return m(this,void 0,void 0,(function*(){const{filePath:t,fileExtension:r,postPurge:s=!1}=e;let o=[];if(!(yield n.stat(t)).isDirectory())return void W.error(`The provided path to reassemble is not a directory: ${t}`);W.debug(`Parsing directory to reassemble: ${t}`);const[l,d]=yield this.processFilesInDirectory(t);o=l;const a=i.dirname(t),c=i.basename(t),u=r?`${c}.${r}`:`${c}.xml`,f=i.join(a,u);if(void 0!==d){const[e,i,r]=d;yield function(e,t,i,r,s){return m(this,void 0,void 0,(function*(){let o=e.join("\n");const l=s.replace(/[.*+?^${}()|[\]\\]/g,"\\$&"),d=new RegExp(`^\\s*${l}\\s*$`,"gm");o=o.replace(d,""),o=o.replace(new RegExp(`<${i}\\s*[^>]*>`,"g"),""),o=o.replace(new RegExp(`</${i}>`,"g"),""),o=o.replace(/<!\[CDATA\[\s*([\s\S]*?)\s*]]>/g,(function(e,t){const n=t.trim().split("\n").map((function(e){return e.replace(/^\s*/,"")}));return"<![CDATA[\n"+p+n.join("\n"+p)+"\n]]>"})),o=o.replace(/(\n\s*){2,}/g,`\n${p}`);const a=`</${i}>`;yield n.writeFile(t,`${s}\n${r}${o}${a}`),W.debug(`Created reassembled file: ${t}`)}))}(o,f,e,i,r),s&&(yield n.rm(t,{recursive:!0}))}else W.error(`No files under ${t} were parsed successfully. A reassembled XML file was not created.`)}))}parseToXmlObject(e){return m(this,void 0,void 0,(function*(){if(e.endsWith(".xml"))return yield $(e);const t=yield n.readFile(e,"utf-8");let i;return e.endsWith(".yaml")||e.endsWith(".yml")?i=r.parse(t):e.endsWith(".json5")?i=s.parse(t):e.endsWith(".json")?i=JSON.parse(t):e.endsWith(".toml")?i=o.parse(t):e.endsWith(".ini")&&(i=l.parse(t)),i}))}},e.buildXMLString=g,e.logger=W,e.parseXML=$,e.setLogLevel=function(e){t.getLogger().level=e}}));
//# sourceMappingURL=index.min.umd.js.map