@jaredwray/fumanchu 4.2.0 → 4.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -1,11 +1,2388 @@
1
- import y from"handlebars";var un=(n,e)=>Array.isArray(n)?n.slice(e):[],bn=(n,e)=>Array.isArray(n)?n.slice(0,-e):[],g=n=>n==null?[]:Array.isArray(n)?n:[n],dn=(n,e)=>{if(Array.isArray(n))return typeof e!="number"?n[0]:n.slice(0,e)},hn=(n,e)=>{if(!Array.isArray(n)&&typeof n!="string")return;if(typeof e!="number"){let t=n;return t[t.length-1]}let r=Math.abs(e);return n.slice(-r)},wn=n=>n&&typeof n=="object"&&!Array.isArray(n)?Object.keys(n).length:typeof n=="string"||Array.isArray(n)?n.length:0,jn=(n,e=", ")=>typeof n=="string"?n:Array.isArray(n)?n.join(e):"",kn=function(n,e){if(!Array.isArray(n)||!e||typeof e.fn!="function")return e?.inverse?e.inverse(this)??"":"";if(n.length===0)return e.inverse?e.inverse(this)??"":"";let r=n.length,t=e.hash??{},o=e.data?{...e.data}:void 0,s="";for(let i=0;i<r;i++){let c=n[i],l={index:i,total:r,isFirst:i===0,isLast:i===r-1},fn={...o?{...o}:{},...t,...l},H;c!=null&&typeof c=="object"?H={...c,...t,...l}:H={value:c,...t,...l},s+=e.fn(H,{data:fn})}return s},$=[{name:"after",category:"array",compatibility:["browser","nodejs"],fn:un},{name:"before",category:"array",compatibility:["browser","nodejs"],fn:bn},{name:"arrayify",category:"array",compatibility:["browser","nodejs"],fn:g},{name:"first",category:"array",compatibility:["browser","nodejs"],fn:dn},{name:"last",category:"array",compatibility:["browser","nodejs"],fn:hn},{name:"length",category:"array",compatibility:["browser","nodejs"],fn:wn},{name:"join",category:"array",compatibility:["browser","nodejs"],fn:jn},{name:"forEach",category:"array",compatibility:["browser","nodejs"],fn:kn}];import Hn from"fs";import xn from"path";import R from"html-tag";import On from"to-gfm-code-block";var An=(n,e)=>{let r=typeof e=="string"?e:xn.extname(n).slice(1),t=Hn.readFileSync(n,"utf8");return(r==="markdown"||r==="md")&&(r="markdown",t=t.split("`").join("&#x60")),`${On(t,r).trim()}
2
- `},Nn=n=>R("script",{src:`https://gist.github.com/${n}.js`}),$n=n=>{if(!n||!n.id)throw new Error("jsfiddle helper expects an `id`");let{id:e,width:r="100%",height:t="300",skin:o="/presentation/",tabs:s="result,js,html,css",allowfullscreen:i="allowfullscreen",frameborder:c="0"}=n,l=`http://jsfiddle.net/${e}/embedded/${s}${o}`;return R("iframe",{width:r,height:t,src:l,allowfullscreen:i,frameborder:c})},S=[{name:"embed",category:"code",compatibility:["nodejs"],fn:An},{name:"gist",category:"code",compatibility:["browser","nodejs"],fn:Nn},{name:"jsfiddle",category:"code",compatibility:["browser","nodejs"],fn:$n}];var Rn=n=>n==null?!0:Array.isArray(n)?n.length===0:typeof n=="object"?Object.keys(n).length===0:!1,Sn=(n,e,r)=>{if(Array.isArray(n)){let t="";for(let o=0;o<n.length;o++)t+=e(n[o],o);return t}if(n&&typeof n=="object"){let t="";for(let o of Object.keys(n))t+=e(n[o],o);return t}return r?r():""},E=[{name:"isEmpty",category:"collection",compatibility:["browser","nodejs"],fn:Rn},{name:"iterate",category:"collection",compatibility:["browser","nodejs"],fn:Sn}];var En=(...n)=>n.every(Boolean),Fn=(n,e,r)=>{switch(e){case"==":return n==r;case"===":return n===r;case"!=":return n!=r;case"!==":return n!==r;case"<":return n<r;case">":return n>r;case"<=":return n<=r;case">=":return n>=r;case"typeof":return typeof n===r;default:throw new Error(`helper {{compare}}: invalid operator: '${e}'`)}},Tn=(n,e,r=0)=>n==null?!1:typeof n=="string"||Array.isArray(n)?n.indexOf(e,r)>-1:typeof n=="object"?e in n:!1,Bn=(...n)=>{for(let e of n)if(e!=null)return e;return""},_n=(n,e)=>n===e,Mn=(n,e)=>n>e,Cn=(n,e)=>n>=e,zn=(n,e)=>n==null||e==null?!1:Array.isArray(n)||typeof n=="string"?n.indexOf(e)>-1:typeof n=="object"?e in n:!1,F=(n,e)=>{if(!n)return!0;let r=Array.isArray(e)?e:e!=null?[e]:["0","false","nada","nil","nay","nah","negative","no","none","nope","nul","null","nix","nyet","uh-uh","veto","zero"],t=typeof n=="string"?n.toLowerCase():null;for(let o of r)if(o===n||t!=null&&o===t)return!0;return!1},Ln=n=>F(n),Pn=n=>!F(n),Un=n=>typeof n=="number"&&n%2===0,In=(n,e)=>typeof n=="number"&&typeof e=="number"&&e%n===0,vn=n=>typeof n=="number"&&Math.abs(n%2)===1,Jn=(n,e)=>n==e,qn=(n,e)=>n!=e,Dn=(n,e)=>n<e,Wn=(n,e)=>n<=e,Gn=(n,e)=>!n&&!e,Yn=n=>!n,Qn=(...n)=>n.some(Boolean),Zn=(n,e)=>n!==e,Kn=(n,e)=>n<=e,Vn=(n,e)=>n>=e,Xn=(n,e)=>n<e,ne=(n,e)=>n>e,T=[{name:"and",category:"comparison",compatibility:["browser","nodejs"],fn:En},{name:"compare",category:"comparison",compatibility:["browser","nodejs"],fn:Fn},{name:"contains",category:"comparison",compatibility:["browser","nodejs"],fn:Tn},{name:"default",category:"comparison",compatibility:["browser","nodejs"],fn:Bn},{name:"eq",category:"comparison",compatibility:["browser","nodejs"],fn:_n},{name:"gt",category:"comparison",compatibility:["browser","nodejs"],fn:Mn},{name:"gte",category:"comparison",compatibility:["browser","nodejs"],fn:Cn},{name:"has",category:"comparison",compatibility:["browser","nodejs"],fn:zn},{name:"isFalsey",category:"comparison",compatibility:["browser","nodejs"],fn:Ln},{name:"isTruthy",category:"comparison",compatibility:["browser","nodejs"],fn:Pn},{name:"ifEven",category:"comparison",compatibility:["browser","nodejs"],fn:Un},{name:"ifNth",category:"comparison",compatibility:["browser","nodejs"],fn:In},{name:"ifOdd",category:"comparison",compatibility:["browser","nodejs"],fn:vn},{name:"is",category:"comparison",compatibility:["browser","nodejs"],fn:Jn},{name:"isnt",category:"comparison",compatibility:["browser","nodejs"],fn:qn},{name:"lt",category:"comparison",compatibility:["browser","nodejs"],fn:Dn},{name:"lte",category:"comparison",compatibility:["browser","nodejs"],fn:Wn},{name:"neither",category:"comparison",compatibility:["browser","nodejs"],fn:Gn},{name:"not",category:"comparison",compatibility:["browser","nodejs"],fn:Yn},{name:"or",category:"comparison",compatibility:["browser","nodejs"],fn:Qn},{name:"unlessEq",category:"comparison",compatibility:["browser","nodejs"],fn:Zn},{name:"unlessGt",category:"comparison",compatibility:["browser","nodejs"],fn:Kn},{name:"unlessLt",category:"comparison",compatibility:["browser","nodejs"],fn:Vn},{name:"unlessGteq",category:"comparison",compatibility:["browser","nodejs"],fn:Xn},{name:"unlessLteq",category:"comparison",compatibility:["browser","nodejs"],fn:ne}];import{parseDate as ee}from"chrono-node";import re from"dayjs";var te=()=>new Date().getFullYear().toString(),B=(n,e)=>{let r=ee(n);if(!r)throw new Error(`Unable to parse date: ${n}`);return re(r).format(e)},_=[{name:"year",category:"date",compatibility:["browser","nodejs"],fn:te},{name:"date",category:"date",compatibility:["browser","nodejs"],fn:B},{name:"moment",category:"date",compatibility:["browser","nodejs"],fn:B}];import x from"fs";import oe from"path";import se from"is-glob";import ie from"micromatch";var ae=(n,e)=>{if(n==null)return"0 B";let r=typeof n=="number"?n:n.length??0;if(!r)return"0 B";let t=typeof e=="number"?e:2,o=["B","kB","MB","GB","TB","PB","EB","ZB","YB"],s=10**t,i=o.length-1;do{let c=10**(i*3);if(c<=r+1)return`${Math.round(r*s/c)/s} ${o[i]}`}while(--i>=0);return`${r} B`},ce=n=>x.readFileSync(n,"utf8"),pe=n=>!!(n&&typeof n=="object"&&"hash"in n),me=(n,e)=>{let r=x.readdirSync(n).map(o=>oe.join(n,o)),t=pe(e)?void 0:e;if(typeof t=="function")return t(r);if(t instanceof RegExp)return r.filter(o=>t.test(o));if(typeof t=="string"){if(se(t))return ie(r,t);if(t==="isFile"||t==="isDirectory")return r.filter(o=>{let s=x.statSync(o);return t==="isFile"?s.isFile():s.isDirectory()})}return r},M=[{name:"fileSize",category:"fs",compatibility:["nodejs"],fn:ae},{name:"read",category:"fs",compatibility:["nodejs"],fn:ce},{name:"readdir",category:"fs",compatibility:["nodejs"],fn:me}];import O from"path";import C from"html-tag";import le from"striptags";var f=(n={})=>Object.keys(n).map(e=>`${e}="${String(n[e]).replace(/^['"]|["']$/g,"")}"`).join(" "),ye=n=>{let e=f(n?.hash??{});return e.trim()?` ${e}`:""},ge=function(n,e){arguments.length<2&&(e=n,n=[]);let r=g(n??[]),t="";return this&&this.options&&(t=this.options.assets||""),e?.hash?.href&&(r=g(e.hash.href)),r.map(o=>{let s=O.extname(o),i=o;return/(^\/\/)|(:\/\/)/.test(o)||(i=O.posix.join(t,o)),s===".less"?`<link type="text/css" rel="stylesheet/less" href="${i}">`:`<link type="text/css" rel="stylesheet" href="${i}">`}).join(`
3
- `)},fe=n=>{if(n&&typeof n=="object"&&!Array.isArray(n)){let r=f(n.hash??{});return`<script${r?` ${r}`:""}></script>`}return typeof n=="string"?`<script src="${n}"></script>`:g(n).map(r=>O.extname(r)===".coffee"?C("script",{type:"text/coffeescript",src:r}):C("script",{src:r})).join(`
4
- `)},ue=n=>typeof n!="string"?"":le(n).trim(),be=(n,e)=>{let r=f(e.hash??{}),t=n.map(s=>typeof s=="string"?s:e.fn(s));return`${r?`<ul ${r}>`:"<ul>"}${t.map(s=>`<li>${s}</li>`).join(`
5
- `)}</ul>`},de=(n,e)=>{let r=f(e.hash??{}),t=n.map(s=>typeof s=="string"?s:e.fn(s));return`${r?`<ol ${r}>`:"<ol>"}${t.map(s=>`<li>${s}</li>`).join(`
6
- `)}</ol>`},he=n=>{let e="",r="",t=n.full||!1,o={alt:n.alt,src:n.thumbnail,width:n.size.width,height:n.size.height},s={id:`image-${n.id}`},i={href:t,rel:"thumbnail"};return n.classes&&(n.classes.image&&(o.class=n.classes.image.join(" ")),n.classes.figure&&(s.class=n.classes.figure.join(" ")),n.classes.link&&(i.class=n.classes.link.join(" "))),e+=`<figure ${f(s)}>
7
- `,r+=`<img ${f(o)}>
8
- `,t?e+=`<a ${f(i)}>
9
- ${r}</a>
10
- `:e+=r,n.caption&&(e+=`<figcaption>${n.caption}</figcaption>
11
- `),e+="</figure>",e},z=[{name:"attr",category:"html",compatibility:["browser","nodejs"],fn:ye},{name:"css",category:"html",compatibility:["nodejs"],fn:ge},{name:"js",category:"html",compatibility:["nodejs"],fn:fe},{name:"sanitize",category:"html",compatibility:["browser","nodejs"],fn:ue},{name:"ul",category:"html",compatibility:["browser","nodejs"],fn:be},{name:"ol",category:"html",compatibility:["browser","nodejs"],fn:de},{name:"thumbnailImage",category:"html",compatibility:["browser","nodejs"],fn:he}];var u=(n,e)=>{if(!n||typeof n!="object")return;let r=Array.isArray(e)?e:e.split("."),t=n;for(let o of r){if(t==null||typeof t!="object")return;t=t[o]}return t},A=(n,e)=>{if(!n||typeof n!="object")return;let r=Array.isArray(e)?e:e.split(".");if(r.length===0)return;let t=n;for(let s=0;s<r.length-1;s++){if(t==null||typeof t!="object")return;t=t[r[s]]}let o=r[r.length-1];if(!(t==null||typeof t!="object"||!(o in t)))return{[o]:t[o]}};var we=function(n,e,r){if(e&&typeof e=="object"&&"hash"in e&&r===void 0&&(r=e,e={}),typeof n!="string")throw new Error('{{i18n}} helper expected "key" to be a string');let t={...this,...e,...r?.hash??{}},o=t.language||t.lang;if(typeof o!="string")throw new TypeError('{{i18n}} helper expected "language" to be a string');let s=t[o];if(typeof s>"u")throw new Error(`{{i18n}} helper cannot find language "${o}"`);let i=u(s,n);if(typeof i>"u")throw new Error('{{i18n}} helper cannot find property "'+String(n)+'" for language "'+o+'"');return String(i)},L=[{name:"i18n",category:"i18n",compatibility:["browser","nodejs"],fn:we}];var je=(n,e,r,t)=>{let o=n>1||n===0?r:e;return t?`${n} ${o}`:o},ke=n=>{let e=Math.abs(Math.round(Number(n))),r=String(n),t=e%100;if([11,12,13].includes(t))return`${r}th`;switch(e%10){case 1:return`${r}st`;case 2:return`${r}nd`;case 3:return`${r}rd`;default:return`${r}th`}},P=[{name:"inflect",category:"inflection",compatibility:["browser","nodejs"],fn:je},{name:"ordinalize",category:"inflection",compatibility:["browser","nodejs"],fn:ke}];import He from"logging-helpers";var{log:xe,ok:Oe,success:Ae,info:Ne,warning:$e,warn:Re,error:Se,danger:Ee,bold:Fe,_debug:Te,_inspect:Be}=He,U=[{name:"log",category:"logging",compatibility:["nodejs"],fn:xe},{name:"ok",category:"logging",compatibility:["nodejs"],fn:Oe},{name:"success",category:"logging",compatibility:["nodejs"],fn:Ae},{name:"info",category:"logging",compatibility:["nodejs"],fn:Ne},{name:"warning",category:"logging",compatibility:["nodejs"],fn:$e},{name:"warn",category:"logging",compatibility:["nodejs"],fn:Re},{name:"error",category:"logging",compatibility:["nodejs"],fn:Se},{name:"danger",category:"logging",compatibility:["nodejs"],fn:Ee},{name:"bold",category:"logging",compatibility:["nodejs"],fn:Fe},{name:"_debug",category:"logging",compatibility:["nodejs"],fn:Te},{name:"_inspect",category:"logging",compatibility:["nodejs"],fn:Be}];import I from"micromatch";var v=(n,e,r)=>{let t=typeof e=="string"?e.split(/, */):e;return I(n,t,r)},_e=(n,e,r)=>I.isMatch(n,e,r),Me=(...n)=>(console.log("the {{mm}} helper is depcrecated and will be removed"),console.log("in handlebars-helpers v1.0.0, please use the {{match}}"),console.log("helper instead."),v(...n)),J=[{name:"match",category:"match",compatibility:["browser","nodejs"],fn:v},{name:"isMatch",category:"match",compatibility:["browser","nodejs"],fn:_e},{name:"mm",category:"match",compatibility:["browser","nodejs"],fn:Me}];var j=n=>typeof n=="number"&&!Number.isNaN(n)||typeof n=="string"&&n.trim()!==""&&!Number.isNaN(Number(n)),a=(n,e="expected a number")=>{if(j(n))return Number(n);throw new TypeError(e)},Ce=n=>{let e=a(n);return Math.abs(e)},ze=(n,e)=>j(n)&&j(e)?Number(n)+Number(e):"",Le=(...n)=>{let e=n.flat().map(r=>Number(r));return D(e)/e.length},Pe=n=>{let e=a(n);return Math.ceil(e)},Ue=(n,e)=>{let r=a(n,"expected the first argument to be a number"),t=a(e,"expected the second argument to be a number");return r/t},Ie=n=>{let e=a(n);return Math.floor(e)},ve=(n,e)=>{let r=a(n,"expected the first argument to be a number"),t=a(e,"expected the second argument to be a number");return r-t},Je=(n,e)=>{let r=a(n,"expected the first argument to be a number"),t=a(e,"expected the second argument to be a number");return r%t},q=(n,e)=>{let r=a(n,"expected the first argument to be a number"),t=a(e,"expected the second argument to be a number");return r*t},qe=(n,e)=>{let r=a(n,"expected the first argument to be a number"),t=a(e,"expected the second argument to be a number");return r+t},De=(n,e)=>{let r=a(n,"expected minimum to be a number"),t=a(e,"expected maximum to be a number");return r+Math.floor(Math.random()*(t-r+1))},We=(n,e)=>n%e,Ge=n=>{let e=a(n);return Math.round(e)},Ye=(n,e)=>{let r=a(n,"expected the first argument to be a number"),t=a(e,"expected the second argument to be a number");return r-t},D=(...n)=>{let e=n.flat(),r=0;for(let t of e)j(t)&&(r+=Number(t));return r},Qe=(n,e)=>q(n,e),W=[{name:"abs",category:"math",compatibility:["browser","nodejs"],fn:Ce},{name:"add",category:"math",compatibility:["browser","nodejs"],fn:ze},{name:"avg",category:"math",compatibility:["browser","nodejs"],fn:Le},{name:"ceil",category:"math",compatibility:["browser","nodejs"],fn:Pe},{name:"divide",category:"math",compatibility:["browser","nodejs"],fn:Ue},{name:"floor",category:"math",compatibility:["browser","nodejs"],fn:Ie},{name:"minus",category:"math",compatibility:["browser","nodejs"],fn:ve},{name:"modulo",category:"math",compatibility:["browser","nodejs"],fn:Je},{name:"multiply",category:"math",compatibility:["browser","nodejs"],fn:q},{name:"plus",category:"math",compatibility:["browser","nodejs"],fn:qe},{name:"random",category:"math",compatibility:["browser","nodejs"],fn:De},{name:"remainder",category:"math",compatibility:["browser","nodejs"],fn:We},{name:"round",category:"math",compatibility:["browser","nodejs"],fn:Ge},{name:"subtract",category:"math",compatibility:["browser","nodejs"],fn:Ye},{name:"sum",category:"math",compatibility:["browser","nodejs"],fn:D},{name:"times",category:"math",compatibility:["browser","nodejs"],fn:Qe}];import N from"fs";import Ze from"path";import Ke from"process";import Ve from"ent";import Xe from"handlebars";import{Remarkable as nr}from"remarkable";var G=function(n,e){typeof n=="object"&&n&&"fn"in n&&typeof n.fn=="function"?(e=n,n=n.fn(this)):typeof n!="string"&&(n="");let r={cwd:Ke.cwd(),...e},t=new nr({breaks:!0,html:!0,langPrefix:"lang-",typographer:!1,xhtmlOut:!1}),o=n;if(o&&o.length>0){let s=Ze.resolve(r.cwd,o);N.existsSync(s)&&N.statSync(s).isFile()&&(o=N.readFileSync(s,"utf8"))}return new Xe.SafeString(Ve.decode(t.render(o)))},Y=[{name:"md",category:"markdown",compatibility:["nodejs"],fn:G},{name:"markdown",category:"markdown",compatibility:["nodejs"],fn:G}];import er from"handlebars-helper-create-frame";import rr from"handlebars-utils";import tr from"kind-of";var or=er;function sr(n,e,r){return u(rr.options(this,e,r),n)}function ir(n){return n.fn(this)}var ar=tr;function cr(n){return n.hash&&Object.keys(n.hash).length?n.fn(n.hash):n.inverse(this)}var Q=[{name:"frame",category:"misc",compatibility:["browser","nodejs"],fn:or},{name:"option",category:"misc",compatibility:["browser","nodejs"],fn:sr},{name:"noop",category:"misc",compatibility:["browser","nodejs"],fn:ir},{name:"typeOf",category:"misc",compatibility:["browser","nodejs"],fn:ar},{name:"withHash",category:"misc",compatibility:["browser","nodejs"],fn:cr}];var h=n=>typeof n=="number"&&!Number.isNaN(n),pr=(n,e)=>{if(n==null)return"0 B";let r;if(typeof n=="string"){if(r=n.length,!r)return"0 B"}else if(h(n))r=Number(n);else if(typeof n.length=="number"){if(r=n.length,!r)return"0 B"}else return"0 B";let t=typeof e=="number"&&!Number.isNaN(e)?e:2,o=["B","kB","MB","GB","TB","PB","EB","ZB","YB"],s=10**t;for(let i=o.length-1;i>=0;i--){let c=10**(i*3);if(c<=r+1)return`${Math.round(r*s/c)/s} ${o[i]}`}return`${r}`},mr=n=>n.toString().replace(/(\d)(?=(\d\d\d)+(?!\d))/g,"$1,"),lr=n=>{let e=n.toString();return`(${e.substr(0,3)}) ${e.substr(3,3)}-${e.substr(6,4)}`},yr=(n,e)=>{let r=h(n)?Number(n):0,o=10**(typeof e=="number"&&!Number.isNaN(e)?e:2),s=["k","m","b","t","q"];for(let i=s.length-1;i>=0;i--){let c=10**((i+1)*3);if(c<=r+1)return`${Math.round(r*o/c)/o}${s[i]}`}return`${r}`},gr=(n,e)=>{let r=h(n)?Number(n):0,t=typeof e=="number"&&!Number.isNaN(e)?e:0;return Number(r).toExponential(t)},fr=(n,e)=>{let r=h(n)?Number(n):0,t=typeof e=="number"&&!Number.isNaN(e)?e:0;return Number(r).toFixed(t)},ur=n=>parseFloat(String(n)),br=n=>parseInt(String(n),10),dr=(n,e)=>{let r=h(n)?Number(n):0,t=typeof e=="number"&&!Number.isNaN(e)?e:1;return Number(r).toPrecision(t)},Z=[{name:"bytes",category:"number",compatibility:["browser","nodejs"],fn:pr},{name:"addCommas",category:"number",compatibility:["browser","nodejs"],fn:mr},{name:"phoneNumber",category:"number",compatibility:["browser","nodejs"],fn:lr},{name:"toAbbr",category:"number",compatibility:["browser","nodejs"],fn:yr},{name:"toExponential",category:"number",compatibility:["browser","nodejs"],fn:gr},{name:"toFixed",category:"number",compatibility:["browser","nodejs"],fn:fr},{name:"toFloat",category:"number",compatibility:["browser","nodejs"],fn:ur},{name:"toInt",category:"number",compatibility:["browser","nodejs"],fn:br},{name:"toPrecision",category:"number",compatibility:["browser","nodejs"],fn:dr}];var k=n=>!!(n&&typeof n=="object"&&"hash"in n),K=(n,e)=>({...n?.data||{},...e}),hr=(...n)=>{let e=[...n];if(e.length&&k(e[e.length-1])){let t=e.pop();e.push(t.hash)}let r={};for(let t of e)t&&typeof t=="object"&&!Array.isArray(t)&&Object.assign(r,t);return r},wr=(n,e)=>{if(!k(e))return e?.inverse?.(n)??"";let r=K(e,e.hash||{}),t="";for(let o in n)r.key=o,t+=e.fn(n[o],{data:r});return t},jr=(n,e)=>{if(!k(e))return e?.inverse?.(n)??"";let r=K(e,e.hash||{}),t="";for(let o in n)Object.hasOwn(n,o)&&(r.key=o,t+=e.fn(n[o],{data:r}));return t},kr=(...n)=>{let e=[];for(let r of n)(typeof r=="string"||typeof r=="number")&&e.push(r);return e.join(".")},Hr=(n,e,r)=>{let t=u(e,n);return r&&typeof r.fn=="function"?t?r.fn(t):r.inverse?.(e):t},xr=(n,e)=>A(e,n),Or=(n,e)=>Object.hasOwn(n,e),Ar=n=>!!n&&typeof n=="object"&&!Array.isArray(n),V=n=>JSON.parse(n),X=(n,e)=>JSON.stringify(n,null,typeof e=="number"?e:0),Nr=(n,...e)=>{let r=[n,...e];if(r.length&&k(r[r.length-1])){let t=r.pop();r.push(t.hash)}return Object.assign(...r)},$r=V,Rr=X,Sr=(n,e,r)=>{let t=g(n),o={};for(let s of t)o=Object.assign({},o,A(e,s));return r&&typeof r.fn=="function"?Object.keys(o).length?r.fn(o):r.inverse?.(e):o},nn=[{name:"extend",category:"object",compatibility:["browser","nodejs"],fn:hr},{name:"forIn",category:"object",compatibility:["browser","nodejs"],fn:wr},{name:"forOwn",category:"object",compatibility:["browser","nodejs"],fn:jr},{name:"toPath",category:"object",compatibility:["browser","nodejs"],fn:kr},{name:"get",category:"object",compatibility:["browser","nodejs"],fn:Hr},{name:"getObject",category:"object",compatibility:["browser","nodejs"],fn:xr},{name:"hasOwn",category:"object",compatibility:["browser","nodejs"],fn:Or},{name:"isObject",category:"object",compatibility:["browser","nodejs"],fn:Ar},{name:"JSONparse",category:"object",compatibility:["browser","nodejs"],fn:V},{name:"JSONstringify",category:"object",compatibility:["browser","nodejs"],fn:X},{name:"merge",category:"object",compatibility:["browser","nodejs"],fn:Nr},{name:"parseJSON",category:"object",compatibility:["browser","nodejs"],fn:$r},{name:"pick",category:"object",compatibility:["browser","nodejs"],fn:Sr},{name:"stringify",category:"object",compatibility:["browser","nodejs"],fn:Rr}];import m from"path";var Er=(n,e,r)=>{let t=Object.prototype.toString.call(r).slice(8,-1).toLowerCase();return`Expected ${n} to be of type ${e}, but got ${t}`},p=(n,e)=>{if(typeof e!="string")throw new TypeError(Er(n,"string",e));return e},Fr=function(n,e){let r=p("filepath",n),t=e?.data?.root?.cwd??this?.cwd??process.cwd();return m.resolve(t,r)},Tr=n=>{let e=p("filepath",n);return m.dirname(e)},Br=(n,e)=>{let r=p("first path",n),t=p("second path",e);return m.relative(m.dirname(r),t)},_r=n=>{let e=p("filepath",n);return m.basename(e)},Mr=n=>{let e=p("filepath",n);return m.basename(e,m.extname(e))},Cr=n=>{let e=p("filepath",n);return m.extname(e)},zr=function(n,...e){let r,t=e[e.length-1];typeof t=="object"&&t&&"data"in t&&(r=e.pop());let s=[r?.data?.root?.cwd??this?.cwd??process.cwd(),p("filepath",n),...e.map((i,c)=>p(`path${c}`,i))];return m.resolve(...s)},Lr=(n,e,r)=>{let t=p("filepath",n),o=Number(e),s=Number(r);return t.split(/[\\/]+/).slice(o,s).join("/")},en=[{name:"absolute",category:"path",compatibility:["nodejs"],fn:Fr},{name:"dirname",category:"path",compatibility:["nodejs"],fn:Tr},{name:"relative",category:"path",compatibility:["nodejs"],fn:Br},{name:"basename",category:"path",compatibility:["nodejs"],fn:_r},{name:"stem",category:"path",compatibility:["nodejs"],fn:Mr},{name:"extname",category:"path",compatibility:["nodejs"],fn:Cr},{name:"resolve",category:"path",compatibility:["nodejs"],fn:zr},{name:"segments",category:"path",compatibility:["nodejs"],fn:Lr}];import Pr from"handlebars-utils";var Ur=(n,e,r)=>{let t=Pr.options({},e,r);return new RegExp(n,t.flags)},Ir=(n,e)=>{if(typeof n!="string")return!1;if(!(e instanceof RegExp))throw new TypeError("expected a regular expression");return e.test(n)},rn=[{name:"toRegex",category:"regex",compatibility:["browser","nodejs"],fn:Ur},{name:"test",category:"regex",compatibility:["browser","nodejs"],fn:Ir}];var tn=n=>n.trim().replace(/^[-_.\W\s]+|[-_.\W\s]+$/g,""),b=(n,e)=>n.length===1?n.toLowerCase():tn(n).toLowerCase().replace(/[-_.\W\s]+(\w|$)/g,(t,o)=>e(o)),vr=(n,e)=>typeof n=="string"&&typeof e=="string"?n+e:n,Jr=n=>typeof n=="string"?b(n,e=>e.toUpperCase()):"",on=n=>typeof n!="string"||n.length===0?"":n.charAt(0).toUpperCase()+n.slice(1),qr=n=>typeof n!="string"?"":n.replace(/\w\S*/g,e=>on(e)),Dr=(n,e)=>{if(typeof n!="string")return"";let r="";for(let t=0;t<e;t++)r+="&nbsp;";return r+n+r},Wr=n=>typeof n=="string"?tn(n):"",Gr=n=>typeof n=="string"?b(n,e=>`-${e}`):"",Yr=n=>typeof n=="string"?b(n,e=>`.${e}`):"",sn=(n,e,r)=>typeof n=="string"?(typeof r!="string"&&(r=""),n.length>e?n.slice(0,e-r.length)+r:n):"",Qr=(n,e)=>typeof n=="string"?n.length<=e?n:`${sn(n,e)}\u2026`:"",Zr=n=>typeof n=="string"?n.split(" ").join("-"):"",Kr=n=>typeof n=="string",an=n=>typeof n=="object"&&n!==null&&"fn"in n&&typeof n.fn=="function"?String(n.fn()).toLowerCase():typeof n!="string"?"":n.toLowerCase(),Vr=(...n)=>an(...n),Xr=(n,e)=>{if(typeof n!="string")return"";let r=e.length,t=n.indexOf(e,0),o=0;for(;t>-1;)o++,t=n.indexOf(e,t+r);return o},nt=n=>{if(typeof n!="string")return"";let e=b(n,r=>r.toUpperCase());return e.charAt(0).toUpperCase()+e.slice(1)},et=n=>typeof n=="string"?b(n,e=>`/${e}`):"",rt=(n,e)=>typeof n!="string"?"":(typeof e!="string"&&(e=" "),n.split(e).join("+")),tt=(n,e)=>typeof n=="string"&&typeof e=="string"?e+n:n,ot=(n,e)=>typeof n!="string"?"":typeof e!="string"?n:n.split(e).join(""),st=(n,e)=>typeof n!="string"?"":typeof e!="string"?n:n.replace(e,""),it=(n,e,r)=>typeof n!="string"?"":typeof e!="string"?n:(typeof r!="string"&&(r=""),n.split(e).join(r)),at=(n,e,r)=>typeof n!="string"?"":typeof e!="string"?n:(typeof r!="string"&&(r=""),n.replace(e,r)),ct=n=>typeof n=="string"?n.split("").reverse().join(""):"",pt=n=>typeof n!="string"?"":n.replace(/((?:\S[^.?!]*)[.?!]*)/g,e=>e.charAt(0).toUpperCase()+e.substr(1).toLowerCase()),mt=n=>typeof n=="string"?b(n,e=>`_${e}`):"",lt=n=>typeof n=="string"?n.trim():"",yt=n=>typeof n=="string"?n.replace(/^\s+/,""):"",gt=n=>typeof n=="string"?n.replace(/\s+$/,""):"",ft=(n,e,r)=>{if(typeof n=="string"&&typeof e=="number"&&Number.isFinite(e)){typeof r!="string"&&(r="...");let t=Math.trunc(e),o=n.split(" ");return t<o.length&&(o=o.slice(0,t)),o.join(" ").trim()+r}return""},ut=ft,cn=n=>typeof n=="object"&&n!==null&&"fn"in n&&typeof n.fn=="function"?String(n.fn()).toUpperCase():typeof n!="string"?"":n.toUpperCase(),bt=(...n)=>cn(...n),pn=[{name:"append",category:"string",compatibility:["browser","nodejs"],fn:vr},{name:"camelcase",category:"string",compatibility:["browser","nodejs"],fn:Jr},{name:"capitalize",category:"string",compatibility:["browser","nodejs"],fn:on},{name:"capitalizeAll",category:"string",compatibility:["browser","nodejs"],fn:qr},{name:"center",category:"string",compatibility:["browser","nodejs"],fn:Dr},{name:"chop",category:"string",compatibility:["browser","nodejs"],fn:Wr},{name:"dashcase",category:"string",compatibility:["browser","nodejs"],fn:Gr},{name:"dotcase",category:"string",compatibility:["browser","nodejs"],fn:Yr},{name:"ellipsis",category:"string",compatibility:["browser","nodejs"],fn:Qr},{name:"hyphenate",category:"string",compatibility:["browser","nodejs"],fn:Zr},{name:"isString",category:"string",compatibility:["browser","nodejs"],fn:Kr},{name:"lowercase",category:"string",compatibility:["browser","nodejs"],fn:an},{name:"downcase",category:"string",compatibility:["browser","nodejs"],fn:Vr},{name:"occurrences",category:"string",compatibility:["browser","nodejs"],fn:Xr},{name:"pascalcase",category:"string",compatibility:["browser","nodejs"],fn:nt},{name:"pathcase",category:"string",compatibility:["browser","nodejs"],fn:et},{name:"plusify",category:"string",compatibility:["browser","nodejs"],fn:rt},{name:"prepend",category:"string",compatibility:["browser","nodejs"],fn:tt},{name:"remove",category:"string",compatibility:["browser","nodejs"],fn:ot},{name:"removeFirst",category:"string",compatibility:["browser","nodejs"],fn:st},{name:"replace",category:"string",compatibility:["browser","nodejs"],fn:it},{name:"replaceFirst",category:"string",compatibility:["browser","nodejs"],fn:at},{name:"reverse",category:"string",compatibility:["browser","nodejs"],fn:ct},{name:"sentence",category:"string",compatibility:["browser","nodejs"],fn:pt},{name:"snakecase",category:"string",compatibility:["browser","nodejs"],fn:mt},{name:"trim",category:"string",compatibility:["browser","nodejs"],fn:lt},{name:"trimLeft",category:"string",compatibility:["browser","nodejs"],fn:yt},{name:"trimRight",category:"string",compatibility:["browser","nodejs"],fn:gt},{name:"truncate",category:"string",compatibility:["browser","nodejs"],fn:sn},{name:"truncateWords",category:"string",compatibility:["browser","nodejs"],fn:ut},{name:"uppercase",category:"string",compatibility:["browser","nodejs"],fn:cn},{name:"upcase",category:"string",compatibility:["browser","nodejs"],fn:bt}];import{escape as dt}from"querystring";import{format as ht,parse as mn,resolve as wt}from"url";var w=["browser","nodejs"],ln=n=>{if(typeof n=="string")return encodeURIComponent(n)},jt=n=>{if(typeof n=="string")return dt(n)},yn=n=>{if(typeof n=="string")return decodeURIComponent(n)};function kt(...n){return ln.apply(this,n)}function Ht(...n){return yn.apply(this,n)}var xt=(n,e)=>wt(String(n),String(e)),Ot=n=>mn(String(n)),At=n=>{if(typeof n=="string")return n.split("?")[0]},Nt=n=>{if(typeof n=="string"){let e=mn(n);return e.protocol="",ht(e)}},gn=[{name:"encodeURI",category:"url",compatibility:w,fn:ln},{name:"escape",category:"url",compatibility:["nodejs"],fn:jt},{name:"decodeURI",category:"url",compatibility:w,fn:yn},{name:"url_encode",category:"url",compatibility:w,fn:kt},{name:"url_decode",category:"url",compatibility:w,fn:Ht},{name:"urlResolve",category:"url",compatibility:["nodejs"],fn:xt},{name:"urlParse",category:"url",compatibility:["nodejs"],fn:Ot},{name:"stripQuerystring",category:"url",compatibility:w,fn:At},{name:"stripProtocol",category:"url",compatibility:["nodejs"],fn:Nt}];var d=class{_helpers=[];constructor(){this.init()}get helpers(){return this._helpers}init(){this.registerHelpers($),this.registerHelpers(E),this.registerHelpers(_),this.registerHelpers(M),this.registerHelpers(S),this.registerHelpers(Y),this.registerHelpers(z),this.registerHelpers(T),this.registerHelpers(L),this.registerHelpers(P),this.registerHelpers(U),this.registerHelpers(J),this.registerHelpers(W),this.registerHelpers(Q),this.registerHelpers(Z),this.registerHelpers(en),this.registerHelpers(rn),this.registerHelpers(pn),this.registerHelpers(gn),this.registerHelpers(nn)}register(e){return this.has(e.name)||this._helpers.push(e),!1}registerHelpers(e){for(let r of e)this.register(r)}has(e){return this._helpers.some(r=>r.name===e)}filter(e){let r=this._helpers;return e.names&&(r=r.filter(t=>e.names?.includes(t.name))),e.categories&&(r=r.filter(t=>e.categories?.includes(t.category))),e.compatibility&&(r=r.filter(t=>t.compatibility?.some(o=>e.compatibility?.includes(o)))),r}load(e,r){let t=this._helpers;r&&(t=this.filter(r));for(let o of t)e.registerHelper(o.name,o.fn)}swap(e){for(let r of this._helpers)e.unregisterHelper(r.name),e.registerHelper(r.name,r.fn)}};var Vo=y,Xo=y.create();function ns(n){new d().load(n.handlebars??n.hbs)}async function es(){let n=new d,e=y.create();return Object.keys(y.partials).length>0&&e.registerPartial(y.partials),n.load(e),process.env.NODE_ENV==="development"&&console.warn("createHandlebars will be deprecated in future versions, use `fumanchu` instead."),e}function rs(n){let e=new d,r=y.create();return n?.handlebars?r=n.handlebars:Object.keys(y.partials).length>0&&r.registerPartial(y.partials),e.load(r),r}export{Vo as Handlebars,d as HelperRegistry,es as createHandlebars,rs as fumanchu,Xo as handlebars,ns as helpers};
1
+ // src/index.ts
2
+ import HandlebarsLib from "handlebars";
3
+
4
+ // src/helpers/array.ts
5
+ var after = (array, n) => {
6
+ if (!Array.isArray(array)) return [];
7
+ return array.slice(n);
8
+ };
9
+ var before = (array, n) => {
10
+ if (!Array.isArray(array)) return [];
11
+ return array.slice(0, -n);
12
+ };
13
+ var arrayify = (value) => {
14
+ if (value == null) return [];
15
+ return Array.isArray(value) ? value : [value];
16
+ };
17
+ var first = (array, n) => {
18
+ if (!Array.isArray(array)) return void 0;
19
+ if (typeof n !== "number") {
20
+ return array[0];
21
+ }
22
+ return array.slice(0, n);
23
+ };
24
+ var last = (value, n) => {
25
+ if (!Array.isArray(value) && typeof value !== "string") {
26
+ return void 0;
27
+ }
28
+ if (typeof n !== "number") {
29
+ const array = value;
30
+ return array[array.length - 1];
31
+ }
32
+ const start = Math.abs(n);
33
+ if (typeof value === "string") {
34
+ return value.slice(-start);
35
+ }
36
+ return value.slice(-start);
37
+ };
38
+ var length = (value) => {
39
+ if (value && typeof value === "object" && !Array.isArray(value)) {
40
+ return Object.keys(value).length;
41
+ }
42
+ if (typeof value === "string" || Array.isArray(value)) {
43
+ return value.length;
44
+ }
45
+ return 0;
46
+ };
47
+ var join = (array, separator = ", ") => {
48
+ if (typeof array === "string") return array;
49
+ if (!Array.isArray(array)) return "";
50
+ return array.join(separator);
51
+ };
52
+ var forEach = function(collection, options) {
53
+ if (!Array.isArray(collection) || !options || typeof options.fn !== "function") {
54
+ return options?.inverse ? options.inverse(this) ?? "" : "";
55
+ }
56
+ if (collection.length === 0) {
57
+ return options.inverse ? options.inverse(this) ?? "" : "";
58
+ }
59
+ const total = collection.length;
60
+ const hash = options.hash ?? {};
61
+ const baseData = options.data ? { ...options.data } : void 0;
62
+ let result = "";
63
+ for (let index = 0; index < total; index++) {
64
+ const value = collection[index];
65
+ const meta = {
66
+ index,
67
+ total,
68
+ isFirst: index === 0,
69
+ isLast: index === total - 1
70
+ };
71
+ const data = {
72
+ ...baseData ? { ...baseData } : {},
73
+ ...hash,
74
+ ...meta
75
+ };
76
+ let context;
77
+ if (value != null && typeof value === "object") {
78
+ context = { ...value, ...hash, ...meta };
79
+ } else {
80
+ context = { value, ...hash, ...meta };
81
+ }
82
+ result += options.fn(context, { data });
83
+ }
84
+ return result;
85
+ };
86
+ var helpers = [
87
+ {
88
+ name: "after",
89
+ category: "array",
90
+ compatibility: ["browser", "nodejs"],
91
+ fn: after
92
+ },
93
+ {
94
+ name: "before",
95
+ category: "array",
96
+ compatibility: ["browser", "nodejs"],
97
+ fn: before
98
+ },
99
+ {
100
+ name: "arrayify",
101
+ category: "array",
102
+ compatibility: ["browser", "nodejs"],
103
+ fn: arrayify
104
+ },
105
+ {
106
+ name: "first",
107
+ category: "array",
108
+ compatibility: ["browser", "nodejs"],
109
+ fn: first
110
+ },
111
+ {
112
+ name: "last",
113
+ category: "array",
114
+ compatibility: ["browser", "nodejs"],
115
+ fn: last
116
+ },
117
+ {
118
+ name: "length",
119
+ category: "array",
120
+ compatibility: ["browser", "nodejs"],
121
+ fn: length
122
+ },
123
+ {
124
+ name: "join",
125
+ category: "array",
126
+ compatibility: ["browser", "nodejs"],
127
+ fn: join
128
+ },
129
+ {
130
+ name: "forEach",
131
+ category: "array",
132
+ compatibility: ["browser", "nodejs"],
133
+ fn: forEach
134
+ }
135
+ ];
136
+
137
+ // src/helpers/code.ts
138
+ import fs from "fs";
139
+ import path from "path";
140
+ import tag from "html-tag";
141
+ import codeBlock from "to-gfm-code-block";
142
+ var embed = (filepath, language) => {
143
+ let ext = typeof language === "string" ? language : path.extname(filepath).slice(1);
144
+ let code = fs.readFileSync(filepath, "utf8");
145
+ if (ext === "markdown" || ext === "md") {
146
+ ext = "markdown";
147
+ code = code.split("`").join("&#x60");
148
+ }
149
+ return `${codeBlock(code, ext).trim()}
150
+ `;
151
+ };
152
+ var gist = (id) => {
153
+ return tag("script", { src: `https://gist.github.com/${id}.js` });
154
+ };
155
+ var jsfiddle = (options) => {
156
+ if (!options || !options.id) {
157
+ throw new Error("jsfiddle helper expects an `id`");
158
+ }
159
+ const {
160
+ id,
161
+ width = "100%",
162
+ height = "300",
163
+ skin = "/presentation/",
164
+ tabs = "result,js,html,css",
165
+ allowfullscreen = "allowfullscreen",
166
+ frameborder = "0"
167
+ } = options;
168
+ const src = `http://jsfiddle.net/${id}/embedded/${tabs}${skin}`;
169
+ return tag("iframe", { width, height, src, allowfullscreen, frameborder });
170
+ };
171
+ var helpers2 = [
172
+ {
173
+ name: "embed",
174
+ category: "code",
175
+ compatibility: ["nodejs"],
176
+ fn: embed
177
+ },
178
+ {
179
+ name: "gist",
180
+ category: "code",
181
+ compatibility: ["browser", "nodejs"],
182
+ fn: gist
183
+ },
184
+ {
185
+ name: "jsfiddle",
186
+ category: "code",
187
+ compatibility: ["browser", "nodejs"],
188
+ fn: jsfiddle
189
+ }
190
+ ];
191
+
192
+ // src/helpers/collection.ts
193
+ var isEmpty = (collection) => {
194
+ if (collection == null) return true;
195
+ if (Array.isArray(collection)) return collection.length === 0;
196
+ if (typeof collection === "object")
197
+ return Object.keys(collection).length === 0;
198
+ return false;
199
+ };
200
+ var iterate = (collection, fn, inverse) => {
201
+ if (Array.isArray(collection)) {
202
+ let result = "";
203
+ for (let i = 0; i < collection.length; i++) {
204
+ result += fn(collection[i], i);
205
+ }
206
+ return result;
207
+ }
208
+ if (collection && typeof collection === "object") {
209
+ let result = "";
210
+ for (const key of Object.keys(collection)) {
211
+ result += fn(collection[key], key);
212
+ }
213
+ return result;
214
+ }
215
+ return inverse ? inverse() : "";
216
+ };
217
+ var helpers3 = [
218
+ {
219
+ name: "isEmpty",
220
+ category: "collection",
221
+ compatibility: ["browser", "nodejs"],
222
+ fn: isEmpty
223
+ },
224
+ {
225
+ name: "iterate",
226
+ category: "collection",
227
+ compatibility: ["browser", "nodejs"],
228
+ fn: iterate
229
+ }
230
+ ];
231
+
232
+ // src/helpers/comparison.ts
233
+ var and = (...values) => values.every(Boolean);
234
+ var compare = (a, operator, b) => {
235
+ switch (operator) {
236
+ case "==":
237
+ return a == b;
238
+ case "===":
239
+ return a === b;
240
+ case "!=":
241
+ return a != b;
242
+ case "!==":
243
+ return a !== b;
244
+ case "<":
245
+ return a < b;
246
+ case ">":
247
+ return a > b;
248
+ case "<=":
249
+ return a <= b;
250
+ case ">=":
251
+ return a >= b;
252
+ case "typeof":
253
+ return typeof a === b;
254
+ default:
255
+ throw new Error(`helper {{compare}}: invalid operator: '${operator}'`);
256
+ }
257
+ };
258
+ var contains = (collection, value, startIndex = 0) => {
259
+ if (collection == null) return false;
260
+ if (typeof collection === "string" || Array.isArray(collection)) {
261
+ return collection.indexOf(value, startIndex) > -1;
262
+ }
263
+ if (typeof collection === "object") {
264
+ return value in collection;
265
+ }
266
+ return false;
267
+ };
268
+ var defaultHelper = (...values) => {
269
+ for (const val of values) {
270
+ if (val != null) return val;
271
+ }
272
+ return "";
273
+ };
274
+ var eq = (a, b) => a === b;
275
+ var gt = (a, b) => a > b;
276
+ var gte = (a, b) => a >= b;
277
+ var has = (value, pattern) => {
278
+ if (value == null || pattern == null) return false;
279
+ if (Array.isArray(value) || typeof value === "string") {
280
+ return value.indexOf(pattern) > -1;
281
+ }
282
+ if (typeof value === "object") {
283
+ return pattern in value;
284
+ }
285
+ return false;
286
+ };
287
+ var falsey = (val, keywords) => {
288
+ if (!val) return true;
289
+ const words = Array.isArray(keywords) ? keywords : keywords != null ? [keywords] : [
290
+ "0",
291
+ "false",
292
+ "nada",
293
+ "nil",
294
+ "nay",
295
+ "nah",
296
+ "negative",
297
+ "no",
298
+ "none",
299
+ "nope",
300
+ "nul",
301
+ "null",
302
+ "nix",
303
+ "nyet",
304
+ "uh-uh",
305
+ "veto",
306
+ "zero"
307
+ ];
308
+ const lower = typeof val === "string" ? val.toLowerCase() : null;
309
+ for (const word of words) {
310
+ if (word === val) return true;
311
+ if (lower != null && word === lower) return true;
312
+ }
313
+ return false;
314
+ };
315
+ var isFalsey = (val) => falsey(val);
316
+ var isTruthy = (val) => !falsey(val);
317
+ var ifEven = (num) => typeof num === "number" && num % 2 === 0;
318
+ var ifNth = (a, b) => typeof a === "number" && typeof b === "number" && b % a === 0;
319
+ var ifOdd = (val) => typeof val === "number" && Math.abs(val % 2) === 1;
320
+ var is = (a, b) => a == b;
321
+ var isnt = (a, b) => a != b;
322
+ var lt = (a, b) => a < b;
323
+ var lte = (a, b) => a <= b;
324
+ var neither = (a, b) => !a && !b;
325
+ var not = (val) => !val;
326
+ var or = (...values) => values.some(Boolean);
327
+ var unlessEq = (a, b) => a !== b;
328
+ var unlessGt = (a, b) => a <= b;
329
+ var unlessLt = (a, b) => a >= b;
330
+ var unlessGteq = (a, b) => a < b;
331
+ var unlessLteq = (a, b) => a > b;
332
+ var helpers4 = [
333
+ {
334
+ name: "and",
335
+ category: "comparison",
336
+ compatibility: ["browser", "nodejs"],
337
+ fn: and
338
+ },
339
+ {
340
+ name: "compare",
341
+ category: "comparison",
342
+ compatibility: ["browser", "nodejs"],
343
+ fn: compare
344
+ },
345
+ {
346
+ name: "contains",
347
+ category: "comparison",
348
+ compatibility: ["browser", "nodejs"],
349
+ fn: contains
350
+ },
351
+ {
352
+ name: "default",
353
+ category: "comparison",
354
+ compatibility: ["browser", "nodejs"],
355
+ fn: defaultHelper
356
+ },
357
+ {
358
+ name: "eq",
359
+ category: "comparison",
360
+ compatibility: ["browser", "nodejs"],
361
+ fn: eq
362
+ },
363
+ {
364
+ name: "gt",
365
+ category: "comparison",
366
+ compatibility: ["browser", "nodejs"],
367
+ fn: gt
368
+ },
369
+ {
370
+ name: "gte",
371
+ category: "comparison",
372
+ compatibility: ["browser", "nodejs"],
373
+ fn: gte
374
+ },
375
+ {
376
+ name: "has",
377
+ category: "comparison",
378
+ compatibility: ["browser", "nodejs"],
379
+ fn: has
380
+ },
381
+ {
382
+ name: "isFalsey",
383
+ category: "comparison",
384
+ compatibility: ["browser", "nodejs"],
385
+ fn: isFalsey
386
+ },
387
+ {
388
+ name: "isTruthy",
389
+ category: "comparison",
390
+ compatibility: ["browser", "nodejs"],
391
+ fn: isTruthy
392
+ },
393
+ {
394
+ name: "ifEven",
395
+ category: "comparison",
396
+ compatibility: ["browser", "nodejs"],
397
+ fn: ifEven
398
+ },
399
+ {
400
+ name: "ifNth",
401
+ category: "comparison",
402
+ compatibility: ["browser", "nodejs"],
403
+ fn: ifNth
404
+ },
405
+ {
406
+ name: "ifOdd",
407
+ category: "comparison",
408
+ compatibility: ["browser", "nodejs"],
409
+ fn: ifOdd
410
+ },
411
+ {
412
+ name: "is",
413
+ category: "comparison",
414
+ compatibility: ["browser", "nodejs"],
415
+ fn: is
416
+ },
417
+ {
418
+ name: "isnt",
419
+ category: "comparison",
420
+ compatibility: ["browser", "nodejs"],
421
+ fn: isnt
422
+ },
423
+ {
424
+ name: "lt",
425
+ category: "comparison",
426
+ compatibility: ["browser", "nodejs"],
427
+ fn: lt
428
+ },
429
+ {
430
+ name: "lte",
431
+ category: "comparison",
432
+ compatibility: ["browser", "nodejs"],
433
+ fn: lte
434
+ },
435
+ {
436
+ name: "neither",
437
+ category: "comparison",
438
+ compatibility: ["browser", "nodejs"],
439
+ fn: neither
440
+ },
441
+ {
442
+ name: "not",
443
+ category: "comparison",
444
+ compatibility: ["browser", "nodejs"],
445
+ fn: not
446
+ },
447
+ {
448
+ name: "or",
449
+ category: "comparison",
450
+ compatibility: ["browser", "nodejs"],
451
+ fn: or
452
+ },
453
+ {
454
+ name: "unlessEq",
455
+ category: "comparison",
456
+ compatibility: ["browser", "nodejs"],
457
+ fn: unlessEq
458
+ },
459
+ {
460
+ name: "unlessGt",
461
+ category: "comparison",
462
+ compatibility: ["browser", "nodejs"],
463
+ fn: unlessGt
464
+ },
465
+ {
466
+ name: "unlessLt",
467
+ category: "comparison",
468
+ compatibility: ["browser", "nodejs"],
469
+ fn: unlessLt
470
+ },
471
+ {
472
+ name: "unlessGteq",
473
+ category: "comparison",
474
+ compatibility: ["browser", "nodejs"],
475
+ fn: unlessGteq
476
+ },
477
+ {
478
+ name: "unlessLteq",
479
+ category: "comparison",
480
+ compatibility: ["browser", "nodejs"],
481
+ fn: unlessLteq
482
+ }
483
+ ];
484
+
485
+ // src/helpers/date.ts
486
+ import { parseDate } from "chrono-node";
487
+ import dayjs from "dayjs";
488
+ var year = () => (/* @__PURE__ */ new Date()).getFullYear().toString();
489
+ var convertFormatString = (format2) => {
490
+ return format2.replace(/yyyy/g, "YYYY").replace(/yy/g, "YY").replace(/dd/g, "DD").replace(/mm/g, "MM").replace(/hh/g, "HH").replace(/ss/g, "SS");
491
+ };
492
+ var date = (humanReadableDate, formatString) => {
493
+ const parsedDate = parseDate(humanReadableDate);
494
+ if (!parsedDate) {
495
+ throw new Error(`Unable to parse date: ${humanReadableDate}`);
496
+ }
497
+ const convertedFormat = convertFormatString(formatString);
498
+ return dayjs(parsedDate).format(convertedFormat);
499
+ };
500
+ var helpers5 = [
501
+ {
502
+ name: "year",
503
+ category: "date",
504
+ compatibility: ["browser", "nodejs"],
505
+ fn: year
506
+ },
507
+ {
508
+ name: "date",
509
+ category: "date",
510
+ compatibility: ["browser", "nodejs"],
511
+ fn: date
512
+ },
513
+ {
514
+ /* Adding this in for legacy support */
515
+ name: "moment",
516
+ category: "date",
517
+ compatibility: ["browser", "nodejs"],
518
+ fn: date
519
+ }
520
+ ];
521
+
522
+ // src/helpers/fs.ts
523
+ import fs2 from "fs";
524
+ import path2 from "path";
525
+ import isGlob from "is-glob";
526
+ import micromatch from "micromatch";
527
+ var fileSize = (value, precision) => {
528
+ if (value == null) return "0 B";
529
+ const number = typeof value === "number" ? value : value.length ?? 0;
530
+ if (!number) return "0 B";
531
+ const precisionNumber = typeof precision === "number" ? precision : 2;
532
+ const abbr = ["B", "kB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB"];
533
+ const factor = 10 ** precisionNumber;
534
+ let i = abbr.length - 1;
535
+ do {
536
+ const size = 10 ** (i * 3);
537
+ if (size <= number + 1) {
538
+ const num = Math.round(number * factor / size) / factor;
539
+ return `${num} ${abbr[i]}`;
540
+ }
541
+ } while (--i >= 0);
542
+ return `${number} B`;
543
+ };
544
+ var read = (filepath) => {
545
+ return fs2.readFileSync(filepath, "utf8");
546
+ };
547
+ var isOptions = (value) => {
548
+ return Boolean(
549
+ value && typeof value === "object" && "hash" in value
550
+ );
551
+ };
552
+ var readdir = (dir, filter) => {
553
+ const files = fs2.readdirSync(dir).map((fp) => path2.join(dir, fp));
554
+ const filterArg = isOptions(filter) ? void 0 : filter;
555
+ if (typeof filterArg === "function") {
556
+ return filterArg(files);
557
+ }
558
+ if (filterArg instanceof RegExp) {
559
+ return files.filter((fp) => filterArg.test(fp));
560
+ }
561
+ if (typeof filterArg === "string") {
562
+ if (isGlob(filterArg)) {
563
+ return micromatch(files, filterArg);
564
+ }
565
+ if (filterArg === "isFile" || filterArg === "isDirectory") {
566
+ return files.filter((fp) => {
567
+ const stat = fs2.statSync(fp);
568
+ return filterArg === "isFile" ? stat.isFile() : stat.isDirectory();
569
+ });
570
+ }
571
+ }
572
+ return files;
573
+ };
574
+ var helpers6 = [
575
+ {
576
+ name: "fileSize",
577
+ category: "fs",
578
+ compatibility: ["nodejs"],
579
+ fn: fileSize
580
+ },
581
+ {
582
+ name: "read",
583
+ category: "fs",
584
+ compatibility: ["nodejs"],
585
+ fn: read
586
+ },
587
+ {
588
+ name: "readdir",
589
+ category: "fs",
590
+ compatibility: ["nodejs"],
591
+ fn: readdir
592
+ }
593
+ ];
594
+
595
+ // src/helpers/html.ts
596
+ import path3 from "path";
597
+ import tag2 from "html-tag";
598
+ import striptags from "striptags";
599
+ var parseAttributes = (hash = {}) => Object.keys(hash).map((key) => `${key}="${String(hash[key]).replace(/^['"]|["']$/g, "")}"`).join(" ");
600
+ var attr = (options) => {
601
+ const val = parseAttributes(options?.hash ?? {});
602
+ return val.trim() ? ` ${val}` : "";
603
+ };
604
+ var css = function(list, options) {
605
+ if (arguments.length < 2) {
606
+ options = list;
607
+ list = [];
608
+ }
609
+ let styles = arrayify(list ?? []);
610
+ let assets = "";
611
+ if (this && this.options) {
612
+ assets = this.options.assets || "";
613
+ }
614
+ if (options?.hash?.href) {
615
+ styles = arrayify(options.hash.href);
616
+ }
617
+ return styles.map((item) => {
618
+ const ext = path3.extname(item);
619
+ let fp = item;
620
+ if (!/(^\/\/)|(:\/\/)/.test(item)) {
621
+ fp = path3.posix.join(assets, item);
622
+ }
623
+ if (ext === ".less") {
624
+ return `<link type="text/css" rel="stylesheet/less" href="${fp}">`;
625
+ }
626
+ return `<link type="text/css" rel="stylesheet" href="${fp}">`;
627
+ }).join("\n");
628
+ };
629
+ var js = (context) => {
630
+ if (context && typeof context === "object" && !Array.isArray(context)) {
631
+ const attrStr = parseAttributes(context.hash ?? {});
632
+ return `<script${attrStr ? ` ${attrStr}` : ""}></script>`;
633
+ }
634
+ if (typeof context === "string") {
635
+ return `<script src="${context}"></script>`;
636
+ }
637
+ const items = arrayify(context);
638
+ return items.map(
639
+ (fp) => path3.extname(fp) === ".coffee" ? tag2("script", { type: "text/coffeescript", src: fp }) : tag2("script", { src: fp })
640
+ ).join("\n");
641
+ };
642
+ var sanitize = (str) => {
643
+ if (typeof str !== "string") return "";
644
+ return striptags(str).trim();
645
+ };
646
+ var ul = (context, options) => {
647
+ const attrs = parseAttributes(options.hash ?? {});
648
+ const items = context.map(
649
+ (item) => typeof item === "string" ? item : options.fn(item)
650
+ );
651
+ const open = attrs ? `<ul ${attrs}>` : "<ul>";
652
+ return `${open}${items.map((i) => `<li>${i}</li>`).join("\n")}</ul>`;
653
+ };
654
+ var ol = (context, options) => {
655
+ const attrs = parseAttributes(options.hash ?? {});
656
+ const items = context.map(
657
+ (item) => typeof item === "string" ? item : options.fn(item)
658
+ );
659
+ const open = attrs ? `<ol ${attrs}>` : "<ol>";
660
+ return `${open}${items.map((i) => `<li>${i}</li>`).join("\n")}</ol>`;
661
+ };
662
+ var thumbnailImage = (context) => {
663
+ let figure = "";
664
+ let image = "";
665
+ const link = context.full || false;
666
+ const imageAttributes = {
667
+ alt: context.alt,
668
+ src: context.thumbnail,
669
+ width: context.size.width,
670
+ height: context.size.height
671
+ };
672
+ const figureAttributes = { id: `image-${context.id}` };
673
+ const linkAttributes = { href: link, rel: "thumbnail" };
674
+ if (context.classes) {
675
+ if (context.classes.image) {
676
+ imageAttributes.class = context.classes.image.join(" ");
677
+ }
678
+ if (context.classes.figure) {
679
+ figureAttributes.class = context.classes.figure.join(" ");
680
+ }
681
+ if (context.classes.link) {
682
+ linkAttributes.class = context.classes.link.join(" ");
683
+ }
684
+ }
685
+ figure += `<figure ${parseAttributes(figureAttributes)}>
686
+ `;
687
+ image += `<img ${parseAttributes(imageAttributes)}>
688
+ `;
689
+ if (link) {
690
+ figure += `<a ${parseAttributes(linkAttributes)}>
691
+ ${image}</a>
692
+ `;
693
+ } else {
694
+ figure += image;
695
+ }
696
+ if (context.caption) {
697
+ figure += `<figcaption>${context.caption}</figcaption>
698
+ `;
699
+ }
700
+ figure += "</figure>";
701
+ return figure;
702
+ };
703
+ var helpers7 = [
704
+ {
705
+ name: "attr",
706
+ category: "html",
707
+ compatibility: ["browser", "nodejs"],
708
+ fn: attr
709
+ },
710
+ {
711
+ name: "css",
712
+ category: "html",
713
+ compatibility: ["nodejs"],
714
+ fn: css
715
+ },
716
+ {
717
+ name: "js",
718
+ category: "html",
719
+ compatibility: ["nodejs"],
720
+ fn: js
721
+ },
722
+ {
723
+ name: "sanitize",
724
+ category: "html",
725
+ compatibility: ["browser", "nodejs"],
726
+ fn: sanitize
727
+ },
728
+ {
729
+ name: "ul",
730
+ category: "html",
731
+ compatibility: ["browser", "nodejs"],
732
+ fn: ul
733
+ },
734
+ {
735
+ name: "ol",
736
+ category: "html",
737
+ compatibility: ["browser", "nodejs"],
738
+ fn: ol
739
+ },
740
+ {
741
+ name: "thumbnailImage",
742
+ category: "html",
743
+ compatibility: ["browser", "nodejs"],
744
+ fn: thumbnailImage
745
+ }
746
+ ];
747
+
748
+ // src/utils.ts
749
+ var get = (object, path6) => {
750
+ if (!object || typeof object !== "object") return void 0;
751
+ const keys = Array.isArray(path6) ? path6 : path6.split(".");
752
+ let result = object;
753
+ for (const key of keys) {
754
+ if (result == null || typeof result !== "object") return void 0;
755
+ result = result[key];
756
+ }
757
+ return result;
758
+ };
759
+ var getObject = (object, path6) => {
760
+ if (!object || typeof object !== "object") return void 0;
761
+ const keys = Array.isArray(path6) ? path6 : path6.split(".");
762
+ if (keys.length === 0) return void 0;
763
+ let current = object;
764
+ for (let i = 0; i < keys.length - 1; i++) {
765
+ if (current == null || typeof current !== "object") return void 0;
766
+ current = current[keys[i]];
767
+ }
768
+ const finalKey = keys[keys.length - 1];
769
+ if (current == null || typeof current !== "object" || !(finalKey in current)) {
770
+ return void 0;
771
+ }
772
+ return { [finalKey]: current[finalKey] };
773
+ };
774
+
775
+ // src/helpers/i18n.ts
776
+ var i18n = function(prop, locals, options) {
777
+ if (locals && typeof locals === "object" && "hash" in locals && options === void 0) {
778
+ options = locals;
779
+ locals = {};
780
+ }
781
+ if (typeof prop !== "string") {
782
+ throw new Error('{{i18n}} helper expected "key" to be a string');
783
+ }
784
+ const context = {
785
+ ...this,
786
+ ...locals,
787
+ ...options?.hash ?? {}
788
+ };
789
+ const lang = context.language || context.lang;
790
+ if (typeof lang !== "string") {
791
+ throw new TypeError('{{i18n}} helper expected "language" to be a string');
792
+ }
793
+ const cache = context[lang];
794
+ if (typeof cache === "undefined") {
795
+ throw new Error(`{{i18n}} helper cannot find language "${lang}"`);
796
+ }
797
+ const result = get(cache, prop);
798
+ if (typeof result === "undefined") {
799
+ throw new Error(
800
+ '{{i18n}} helper cannot find property "' + String(prop) + '" for language "' + lang + '"'
801
+ );
802
+ }
803
+ return String(result);
804
+ };
805
+ var helpers8 = [
806
+ {
807
+ name: "i18n",
808
+ category: "i18n",
809
+ compatibility: ["browser", "nodejs"],
810
+ fn: i18n
811
+ }
812
+ ];
813
+
814
+ // src/helpers/inflection.ts
815
+ var inflect = (count, singular, plural, includeCount) => {
816
+ const word = count > 1 || count === 0 ? plural : singular;
817
+ return includeCount ? `${count} ${word}` : word;
818
+ };
819
+ var ordinalize = (value) => {
820
+ const num = Math.abs(Math.round(Number(value)));
821
+ const str = String(value);
822
+ const res = num % 100;
823
+ if ([11, 12, 13].includes(res)) {
824
+ return `${str}th`;
825
+ }
826
+ switch (num % 10) {
827
+ case 1:
828
+ return `${str}st`;
829
+ case 2:
830
+ return `${str}nd`;
831
+ case 3:
832
+ return `${str}rd`;
833
+ default:
834
+ return `${str}th`;
835
+ }
836
+ };
837
+ var helpers9 = [
838
+ {
839
+ name: "inflect",
840
+ category: "inflection",
841
+ compatibility: ["browser", "nodejs"],
842
+ fn: inflect
843
+ },
844
+ {
845
+ name: "ordinalize",
846
+ category: "inflection",
847
+ compatibility: ["browser", "nodejs"],
848
+ fn: ordinalize
849
+ }
850
+ ];
851
+
852
+ // src/helpers/logging.ts
853
+ var colors = {
854
+ green: (str) => `\x1B[32m${str}\x1B[0m`,
855
+ cyan: (str) => `\x1B[36m${str}\x1B[0m`,
856
+ yellow: (str) => `\x1B[33m${str}\x1B[0m`,
857
+ red: (str) => `\x1B[31m${str}\x1B[0m`,
858
+ bold: (str) => `\x1B[1m${str}\x1B[0m`
859
+ };
860
+ function cleanArgs(args) {
861
+ const last2 = args[args.length - 1];
862
+ if (args.length > 1 && typeof last2 === "object" && last2 !== null && "hash" in last2) {
863
+ return args.slice(0, -1);
864
+ }
865
+ return args;
866
+ }
867
+ function log(...args) {
868
+ const cleanedArgs = cleanArgs(args);
869
+ console.log(...cleanedArgs);
870
+ return "";
871
+ }
872
+ function ok(...args) {
873
+ const cleanedArgs = cleanArgs(args);
874
+ const message = cleanedArgs.join(" ");
875
+ console.log(colors.green(`\u2713 ${message}`));
876
+ return "";
877
+ }
878
+ function success(...args) {
879
+ const cleanedArgs = cleanArgs(args);
880
+ const message = cleanedArgs.map((arg) => String(arg)).join(" ");
881
+ console.log(colors.green(message));
882
+ return "";
883
+ }
884
+ function info(...args) {
885
+ const cleanedArgs = cleanArgs(args);
886
+ const message = cleanedArgs.map((arg) => String(arg)).join(" ");
887
+ console.log(colors.cyan(message));
888
+ return "";
889
+ }
890
+ function warning(...args) {
891
+ const cleanedArgs = cleanArgs(args);
892
+ const message = cleanedArgs.map((arg) => String(arg)).join(" ");
893
+ console.error(colors.yellow(message));
894
+ return "";
895
+ }
896
+ var warn = warning;
897
+ function error(...args) {
898
+ const cleanedArgs = cleanArgs(args);
899
+ const message = cleanedArgs.map((arg) => String(arg)).join(" ");
900
+ console.error(colors.red(message));
901
+ return "";
902
+ }
903
+ var danger = error;
904
+ function bold(...args) {
905
+ const cleanedArgs = cleanArgs(args);
906
+ const message = cleanedArgs.map((arg) => String(arg)).join(" ");
907
+ console.error(colors.bold(message));
908
+ return "";
909
+ }
910
+ function _debug(...args) {
911
+ const separator = "\u2500".repeat(50);
912
+ console.error(colors.cyan(separator));
913
+ if (args.length > 0) {
914
+ const cleanedArgs = cleanArgs(args);
915
+ console.error(colors.cyan("VALUE:"), cleanedArgs[0]);
916
+ }
917
+ if (this && Object.keys(this).length > 0) {
918
+ console.error(colors.cyan("CONTEXT:"), this);
919
+ }
920
+ console.error(colors.cyan(separator));
921
+ return "";
922
+ }
923
+ function _inspect(context, options) {
924
+ const val = JSON.stringify(context, null, 2);
925
+ const type = options?.hash?.type || "html";
926
+ return switchOutput(type, val);
927
+ }
928
+ function switchOutput(type, json) {
929
+ if (type[0] === ".") {
930
+ type = type.slice(1);
931
+ }
932
+ switch (type) {
933
+ case "md":
934
+ return `
935
+ \`\`\`json
936
+ ${json}
937
+ \`\`\`
938
+ `;
939
+ case "html":
940
+ return `<div class="highlight highlight-json">
941
+ <pre><code>
942
+ ${json}</code></pre></div>`;
943
+ default:
944
+ return json;
945
+ }
946
+ }
947
+ var helpers10 = [
948
+ {
949
+ name: "log",
950
+ category: "logging",
951
+ compatibility: ["nodejs"],
952
+ fn: log
953
+ },
954
+ {
955
+ name: "ok",
956
+ category: "logging",
957
+ compatibility: ["nodejs"],
958
+ fn: ok
959
+ },
960
+ {
961
+ name: "success",
962
+ category: "logging",
963
+ compatibility: ["nodejs"],
964
+ fn: success
965
+ },
966
+ {
967
+ name: "info",
968
+ category: "logging",
969
+ compatibility: ["nodejs"],
970
+ fn: info
971
+ },
972
+ {
973
+ name: "warning",
974
+ category: "logging",
975
+ compatibility: ["nodejs"],
976
+ fn: warning
977
+ },
978
+ {
979
+ name: "warn",
980
+ category: "logging",
981
+ compatibility: ["nodejs"],
982
+ fn: warn
983
+ },
984
+ {
985
+ name: "error",
986
+ category: "logging",
987
+ compatibility: ["nodejs"],
988
+ fn: error
989
+ },
990
+ {
991
+ name: "danger",
992
+ category: "logging",
993
+ compatibility: ["nodejs"],
994
+ fn: danger
995
+ },
996
+ {
997
+ name: "bold",
998
+ category: "logging",
999
+ compatibility: ["nodejs"],
1000
+ fn: bold
1001
+ },
1002
+ {
1003
+ name: "_debug",
1004
+ category: "logging",
1005
+ compatibility: ["nodejs"],
1006
+ fn: _debug
1007
+ },
1008
+ {
1009
+ name: "_inspect",
1010
+ category: "logging",
1011
+ compatibility: ["nodejs"],
1012
+ fn: _inspect
1013
+ }
1014
+ ];
1015
+
1016
+ // src/helpers/match.ts
1017
+ import micromatch2 from "micromatch";
1018
+ var match = (files, patterns, options) => {
1019
+ const pats = typeof patterns === "string" ? patterns.split(/, */) : patterns;
1020
+ return micromatch2(files, pats, options);
1021
+ };
1022
+ var isMatch = (filepath, pattern, options) => {
1023
+ return micromatch2.isMatch(filepath, pattern, options);
1024
+ };
1025
+ var mm = (...args) => {
1026
+ console.log("the {{mm}} helper is depcrecated and will be removed");
1027
+ console.log("in handlebars-helpers v1.0.0, please use the {{match}}");
1028
+ console.log("helper instead.");
1029
+ return match(...args);
1030
+ };
1031
+ var helpers11 = [
1032
+ {
1033
+ name: "match",
1034
+ category: "match",
1035
+ compatibility: ["browser", "nodejs"],
1036
+ fn: match
1037
+ },
1038
+ {
1039
+ name: "isMatch",
1040
+ category: "match",
1041
+ compatibility: ["browser", "nodejs"],
1042
+ fn: isMatch
1043
+ },
1044
+ {
1045
+ name: "mm",
1046
+ category: "match",
1047
+ compatibility: ["browser", "nodejs"],
1048
+ fn: mm
1049
+ }
1050
+ ];
1051
+
1052
+ // src/helpers/math.ts
1053
+ var isNumeric = (value) => typeof value === "number" && !Number.isNaN(value) || typeof value === "string" && value.trim() !== "" && !Number.isNaN(Number(value));
1054
+ var toNumber = (value, message = "expected a number") => {
1055
+ if (isNumeric(value)) {
1056
+ return Number(value);
1057
+ }
1058
+ throw new TypeError(message);
1059
+ };
1060
+ var abs = (value) => {
1061
+ const num = toNumber(value);
1062
+ return Math.abs(num);
1063
+ };
1064
+ var add = (a, b) => {
1065
+ if (isNumeric(a) && isNumeric(b)) {
1066
+ return Number(a) + Number(b);
1067
+ }
1068
+ return "";
1069
+ };
1070
+ var avg = (...values) => {
1071
+ const flat = values.flat().map((n) => Number(n));
1072
+ return sum(flat) / flat.length;
1073
+ };
1074
+ var ceil = (value) => {
1075
+ const num = toNumber(value);
1076
+ return Math.ceil(num);
1077
+ };
1078
+ var divide = (a, b) => {
1079
+ const numA = toNumber(a, "expected the first argument to be a number");
1080
+ const numB = toNumber(b, "expected the second argument to be a number");
1081
+ return numA / numB;
1082
+ };
1083
+ var floor = (value) => {
1084
+ const num = toNumber(value);
1085
+ return Math.floor(num);
1086
+ };
1087
+ var minus = (a, b) => {
1088
+ const numA = toNumber(a, "expected the first argument to be a number");
1089
+ const numB = toNumber(b, "expected the second argument to be a number");
1090
+ return numA - numB;
1091
+ };
1092
+ var modulo = (a, b) => {
1093
+ const numA = toNumber(a, "expected the first argument to be a number");
1094
+ const numB = toNumber(b, "expected the second argument to be a number");
1095
+ return numA % numB;
1096
+ };
1097
+ var multiply = (a, b) => {
1098
+ const numA = toNumber(a, "expected the first argument to be a number");
1099
+ const numB = toNumber(b, "expected the second argument to be a number");
1100
+ return numA * numB;
1101
+ };
1102
+ var plus = (a, b) => {
1103
+ const numA = toNumber(a, "expected the first argument to be a number");
1104
+ const numB = toNumber(b, "expected the second argument to be a number");
1105
+ return numA + numB;
1106
+ };
1107
+ var random = (min, max) => {
1108
+ const minNum = toNumber(min, "expected minimum to be a number");
1109
+ const maxNum = toNumber(max, "expected maximum to be a number");
1110
+ return minNum + Math.floor(Math.random() * (maxNum - minNum + 1));
1111
+ };
1112
+ var remainder = (a, b) => a % b;
1113
+ var round = (value) => {
1114
+ const num = toNumber(value);
1115
+ return Math.round(num);
1116
+ };
1117
+ var subtract = (a, b) => {
1118
+ const numA = toNumber(a, "expected the first argument to be a number");
1119
+ const numB = toNumber(b, "expected the second argument to be a number");
1120
+ return numA - numB;
1121
+ };
1122
+ var sum = (...values) => {
1123
+ const flat = values.flat();
1124
+ let total = 0;
1125
+ for (const value of flat) {
1126
+ if (isNumeric(value)) {
1127
+ total += Number(value);
1128
+ }
1129
+ }
1130
+ return total;
1131
+ };
1132
+ var times = (a, b) => multiply(a, b);
1133
+ var helpers12 = [
1134
+ {
1135
+ name: "abs",
1136
+ category: "math",
1137
+ compatibility: ["browser", "nodejs"],
1138
+ fn: abs
1139
+ },
1140
+ {
1141
+ name: "add",
1142
+ category: "math",
1143
+ compatibility: ["browser", "nodejs"],
1144
+ fn: add
1145
+ },
1146
+ {
1147
+ name: "avg",
1148
+ category: "math",
1149
+ compatibility: ["browser", "nodejs"],
1150
+ fn: avg
1151
+ },
1152
+ {
1153
+ name: "ceil",
1154
+ category: "math",
1155
+ compatibility: ["browser", "nodejs"],
1156
+ fn: ceil
1157
+ },
1158
+ {
1159
+ name: "divide",
1160
+ category: "math",
1161
+ compatibility: ["browser", "nodejs"],
1162
+ fn: divide
1163
+ },
1164
+ {
1165
+ name: "floor",
1166
+ category: "math",
1167
+ compatibility: ["browser", "nodejs"],
1168
+ fn: floor
1169
+ },
1170
+ {
1171
+ name: "minus",
1172
+ category: "math",
1173
+ compatibility: ["browser", "nodejs"],
1174
+ fn: minus
1175
+ },
1176
+ {
1177
+ name: "modulo",
1178
+ category: "math",
1179
+ compatibility: ["browser", "nodejs"],
1180
+ fn: modulo
1181
+ },
1182
+ {
1183
+ name: "multiply",
1184
+ category: "math",
1185
+ compatibility: ["browser", "nodejs"],
1186
+ fn: multiply
1187
+ },
1188
+ {
1189
+ name: "plus",
1190
+ category: "math",
1191
+ compatibility: ["browser", "nodejs"],
1192
+ fn: plus
1193
+ },
1194
+ {
1195
+ name: "random",
1196
+ category: "math",
1197
+ compatibility: ["browser", "nodejs"],
1198
+ fn: random
1199
+ },
1200
+ {
1201
+ name: "remainder",
1202
+ category: "math",
1203
+ compatibility: ["browser", "nodejs"],
1204
+ fn: remainder
1205
+ },
1206
+ {
1207
+ name: "round",
1208
+ category: "math",
1209
+ compatibility: ["browser", "nodejs"],
1210
+ fn: round
1211
+ },
1212
+ {
1213
+ name: "subtract",
1214
+ category: "math",
1215
+ compatibility: ["browser", "nodejs"],
1216
+ fn: subtract
1217
+ },
1218
+ {
1219
+ name: "sum",
1220
+ category: "math",
1221
+ compatibility: ["browser", "nodejs"],
1222
+ fn: sum
1223
+ },
1224
+ {
1225
+ name: "times",
1226
+ category: "math",
1227
+ compatibility: ["browser", "nodejs"],
1228
+ fn: times
1229
+ }
1230
+ ];
1231
+
1232
+ // src/helpers/md.ts
1233
+ import fs3 from "fs";
1234
+ import path4 from "path";
1235
+ import process2 from "process";
1236
+ import ent from "ent";
1237
+ import Handlebars from "handlebars";
1238
+ import { Remarkable } from "remarkable";
1239
+ var renderMarkdown = function(input, options) {
1240
+ if (typeof input === "object" && input && "fn" in input && typeof input.fn === "function") {
1241
+ options = input;
1242
+ input = input.fn(this);
1243
+ } else if (typeof input !== "string") {
1244
+ input = "";
1245
+ }
1246
+ const options_ = { cwd: process2.cwd(), ...options };
1247
+ const md = new Remarkable({
1248
+ breaks: true,
1249
+ html: true,
1250
+ langPrefix: "lang-",
1251
+ typographer: false,
1252
+ xhtmlOut: false
1253
+ });
1254
+ let string_ = input;
1255
+ if (string_ && string_.length > 0) {
1256
+ const filepath = path4.resolve(options_.cwd, string_);
1257
+ if (fs3.existsSync(filepath) && fs3.statSync(filepath).isFile()) {
1258
+ string_ = fs3.readFileSync(filepath, "utf8");
1259
+ }
1260
+ }
1261
+ return new Handlebars.SafeString(ent.decode(md.render(string_)));
1262
+ };
1263
+ var helpers13 = [
1264
+ {
1265
+ name: "md",
1266
+ category: "markdown",
1267
+ compatibility: ["nodejs"],
1268
+ fn: renderMarkdown
1269
+ },
1270
+ {
1271
+ name: "markdown",
1272
+ category: "markdown",
1273
+ compatibility: ["nodejs"],
1274
+ fn: renderMarkdown
1275
+ }
1276
+ ];
1277
+
1278
+ // src/helpers/misc.ts
1279
+ import Handlebars2 from "handlebars";
1280
+ import util from "handlebars-utils";
1281
+ import kindOf from "kind-of";
1282
+ function frame(context, options) {
1283
+ if (typeof context === "object" && context !== null && "hash" in context) {
1284
+ options = context;
1285
+ context = options.data;
1286
+ }
1287
+ const data = Handlebars2.createFrame(context || {});
1288
+ if (typeof options !== "object" || options === null) {
1289
+ options = {};
1290
+ }
1291
+ if (options.hash && typeof options.hash === "object") {
1292
+ Object.assign(data, options.hash);
1293
+ }
1294
+ return options.fn(this, { data });
1295
+ }
1296
+ function option(prop, locals, options) {
1297
+ return get(util.options(this, locals, options), prop);
1298
+ }
1299
+ function noop(options) {
1300
+ return options.fn(this);
1301
+ }
1302
+ var typeOf = kindOf;
1303
+ function withHash(options) {
1304
+ if (options.hash && Object.keys(options.hash).length) {
1305
+ return options.fn(options.hash);
1306
+ }
1307
+ return options.inverse(this);
1308
+ }
1309
+ var helpers14 = [
1310
+ {
1311
+ name: "frame",
1312
+ category: "misc",
1313
+ compatibility: ["browser", "nodejs"],
1314
+ fn: frame
1315
+ },
1316
+ {
1317
+ name: "option",
1318
+ category: "misc",
1319
+ compatibility: ["browser", "nodejs"],
1320
+ fn: option
1321
+ },
1322
+ {
1323
+ name: "noop",
1324
+ category: "misc",
1325
+ compatibility: ["browser", "nodejs"],
1326
+ fn: noop
1327
+ },
1328
+ {
1329
+ name: "typeOf",
1330
+ category: "misc",
1331
+ compatibility: ["browser", "nodejs"],
1332
+ fn: typeOf
1333
+ },
1334
+ {
1335
+ name: "withHash",
1336
+ category: "misc",
1337
+ compatibility: ["browser", "nodejs"],
1338
+ fn: withHash
1339
+ }
1340
+ ];
1341
+
1342
+ // src/helpers/number.ts
1343
+ var isNumeric2 = (value) => typeof value === "number" && !Number.isNaN(value);
1344
+ var bytes = (value, precision) => {
1345
+ if (value == null) return "0 B";
1346
+ let num;
1347
+ if (typeof value === "string") {
1348
+ num = value.length;
1349
+ if (!num) return "0 B";
1350
+ } else if (isNumeric2(value)) {
1351
+ num = Number(value);
1352
+ } else if (typeof value.length === "number") {
1353
+ num = value.length;
1354
+ if (!num) return "0 B";
1355
+ } else {
1356
+ return "0 B";
1357
+ }
1358
+ const prec = typeof precision === "number" && !Number.isNaN(precision) ? precision : 2;
1359
+ const abbr = ["B", "kB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB"];
1360
+ const factor = 10 ** prec;
1361
+ for (let i = abbr.length - 1; i >= 0; i--) {
1362
+ const size = 10 ** (i * 3);
1363
+ if (size <= num + 1) {
1364
+ const val = Math.round(num * factor / size) / factor;
1365
+ return `${val} ${abbr[i]}`;
1366
+ }
1367
+ }
1368
+ return `${num}`;
1369
+ };
1370
+ var addCommas = (num) => num.toString().replace(/(\d)(?=(\d\d\d)+(?!\d))/g, "$1,");
1371
+ var phoneNumber = (num) => {
1372
+ const str = num.toString();
1373
+ return `(${str.substr(0, 3)}) ${str.substr(3, 3)}-${str.substr(6, 4)}`;
1374
+ };
1375
+ var toAbbr = (value, precision) => {
1376
+ const num = isNumeric2(value) ? Number(value) : 0;
1377
+ const prec = typeof precision === "number" && !Number.isNaN(precision) ? precision : 2;
1378
+ const factor = 10 ** prec;
1379
+ const abbr = ["k", "m", "b", "t", "q"];
1380
+ for (let i = abbr.length - 1; i >= 0; i--) {
1381
+ const size = 10 ** ((i + 1) * 3);
1382
+ if (size <= num + 1) {
1383
+ const val = Math.round(num * factor / size) / factor;
1384
+ return `${val}${abbr[i]}`;
1385
+ }
1386
+ }
1387
+ return `${num}`;
1388
+ };
1389
+ var toExponential = (value, digits) => {
1390
+ const num = isNumeric2(value) ? Number(value) : 0;
1391
+ const d = typeof digits === "number" && !Number.isNaN(digits) ? digits : 0;
1392
+ return Number(num).toExponential(d);
1393
+ };
1394
+ var toFixed = (value, digits) => {
1395
+ const num = isNumeric2(value) ? Number(value) : 0;
1396
+ const d = typeof digits === "number" && !Number.isNaN(digits) ? digits : 0;
1397
+ return Number(num).toFixed(d);
1398
+ };
1399
+ var toFloat = (value) => parseFloat(String(value));
1400
+ var toInt = (value) => parseInt(String(value), 10);
1401
+ var toPrecision = (value, precision) => {
1402
+ const num = isNumeric2(value) ? Number(value) : 0;
1403
+ const prec = typeof precision === "number" && !Number.isNaN(precision) ? precision : 1;
1404
+ return Number(num).toPrecision(prec);
1405
+ };
1406
+ var helpers15 = [
1407
+ {
1408
+ name: "bytes",
1409
+ category: "number",
1410
+ compatibility: ["browser", "nodejs"],
1411
+ fn: bytes
1412
+ },
1413
+ {
1414
+ name: "addCommas",
1415
+ category: "number",
1416
+ compatibility: ["browser", "nodejs"],
1417
+ fn: addCommas
1418
+ },
1419
+ {
1420
+ name: "phoneNumber",
1421
+ category: "number",
1422
+ compatibility: ["browser", "nodejs"],
1423
+ fn: phoneNumber
1424
+ },
1425
+ {
1426
+ name: "toAbbr",
1427
+ category: "number",
1428
+ compatibility: ["browser", "nodejs"],
1429
+ fn: toAbbr
1430
+ },
1431
+ {
1432
+ name: "toExponential",
1433
+ category: "number",
1434
+ compatibility: ["browser", "nodejs"],
1435
+ fn: toExponential
1436
+ },
1437
+ {
1438
+ name: "toFixed",
1439
+ category: "number",
1440
+ compatibility: ["browser", "nodejs"],
1441
+ fn: toFixed
1442
+ },
1443
+ {
1444
+ name: "toFloat",
1445
+ category: "number",
1446
+ compatibility: ["browser", "nodejs"],
1447
+ fn: toFloat
1448
+ },
1449
+ {
1450
+ name: "toInt",
1451
+ category: "number",
1452
+ compatibility: ["browser", "nodejs"],
1453
+ fn: toInt
1454
+ },
1455
+ {
1456
+ name: "toPrecision",
1457
+ category: "number",
1458
+ compatibility: ["browser", "nodejs"],
1459
+ fn: toPrecision
1460
+ }
1461
+ ];
1462
+
1463
+ // src/helpers/object.ts
1464
+ var isOptions2 = (value) => {
1465
+ return Boolean(value && typeof value === "object" && "hash" in value);
1466
+ };
1467
+ var createFrame = (options, hash) => ({
1468
+ ...options?.data || {},
1469
+ ...hash
1470
+ });
1471
+ var extend = (...objects) => {
1472
+ const args = [...objects];
1473
+ if (args.length && isOptions2(args[args.length - 1])) {
1474
+ const opts = args.pop();
1475
+ args.push(opts.hash);
1476
+ }
1477
+ const result = {};
1478
+ for (const obj of args) {
1479
+ if (obj && typeof obj === "object" && !Array.isArray(obj)) {
1480
+ Object.assign(result, obj);
1481
+ }
1482
+ }
1483
+ return result;
1484
+ };
1485
+ var forIn = (obj, options) => {
1486
+ if (!isOptions2(options)) {
1487
+ return options?.inverse?.(obj) ?? "";
1488
+ }
1489
+ const data = createFrame(options, options.hash || {});
1490
+ let result = "";
1491
+ for (const key in obj) {
1492
+ data.key = key;
1493
+ result += options.fn(obj[key], { data });
1494
+ }
1495
+ return result;
1496
+ };
1497
+ var forOwn = (obj, options) => {
1498
+ if (!isOptions2(options)) {
1499
+ return options?.inverse?.(obj) ?? "";
1500
+ }
1501
+ const data = createFrame(options, options.hash || {});
1502
+ let result = "";
1503
+ for (const key in obj) {
1504
+ if (Object.hasOwn(obj, key)) {
1505
+ data.key = key;
1506
+ result += options.fn(obj[key], { data });
1507
+ }
1508
+ }
1509
+ return result;
1510
+ };
1511
+ var toPath = (...prop) => {
1512
+ const parts = [];
1513
+ for (const p of prop) {
1514
+ if (typeof p === "string" || typeof p === "number") {
1515
+ parts.push(p);
1516
+ }
1517
+ }
1518
+ return parts.join(".");
1519
+ };
1520
+ var getHelper = (prop, context, options) => {
1521
+ const val = get(context, prop);
1522
+ if (options && typeof options.fn === "function") {
1523
+ return val ? options.fn(val) : options.inverse?.(context);
1524
+ }
1525
+ return val;
1526
+ };
1527
+ var getObjectHelper = (prop, context) => {
1528
+ return getObject(context, prop);
1529
+ };
1530
+ var hasOwn = (context, key) => {
1531
+ return Object.hasOwn(context, key);
1532
+ };
1533
+ var isObject = (value) => {
1534
+ return Boolean(value) && typeof value === "object" && !Array.isArray(value);
1535
+ };
1536
+ var JSONparse = (str) => {
1537
+ return JSON.parse(str);
1538
+ };
1539
+ var JSONstringify = (obj, indent) => {
1540
+ const ind = typeof indent === "number" ? indent : 0;
1541
+ return JSON.stringify(obj, null, ind);
1542
+ };
1543
+ var merge = (context, ...objects) => {
1544
+ const args = [context, ...objects];
1545
+ if (args.length && isOptions2(args[args.length - 1])) {
1546
+ const opts = args.pop();
1547
+ args.push(opts.hash);
1548
+ }
1549
+ return Object.assign(...args);
1550
+ };
1551
+ var parseJSON = JSONparse;
1552
+ var stringify = JSONstringify;
1553
+ var pick = (props, context, options) => {
1554
+ const keys = arrayify(props);
1555
+ let result = {};
1556
+ for (const key of keys) {
1557
+ result = Object.assign({}, result, getObject(context, key));
1558
+ }
1559
+ if (options && typeof options.fn === "function") {
1560
+ if (Object.keys(result).length) {
1561
+ return options.fn(result);
1562
+ }
1563
+ return options.inverse?.(context);
1564
+ }
1565
+ return result;
1566
+ };
1567
+ var helpers16 = [
1568
+ {
1569
+ name: "extend",
1570
+ category: "object",
1571
+ compatibility: ["browser", "nodejs"],
1572
+ fn: extend
1573
+ },
1574
+ {
1575
+ name: "forIn",
1576
+ category: "object",
1577
+ compatibility: ["browser", "nodejs"],
1578
+ fn: forIn
1579
+ },
1580
+ {
1581
+ name: "forOwn",
1582
+ category: "object",
1583
+ compatibility: ["browser", "nodejs"],
1584
+ fn: forOwn
1585
+ },
1586
+ {
1587
+ name: "toPath",
1588
+ category: "object",
1589
+ compatibility: ["browser", "nodejs"],
1590
+ fn: toPath
1591
+ },
1592
+ {
1593
+ name: "get",
1594
+ category: "object",
1595
+ compatibility: ["browser", "nodejs"],
1596
+ fn: getHelper
1597
+ },
1598
+ {
1599
+ name: "getObject",
1600
+ category: "object",
1601
+ compatibility: ["browser", "nodejs"],
1602
+ fn: getObjectHelper
1603
+ },
1604
+ {
1605
+ name: "hasOwn",
1606
+ category: "object",
1607
+ compatibility: ["browser", "nodejs"],
1608
+ fn: hasOwn
1609
+ },
1610
+ {
1611
+ name: "isObject",
1612
+ category: "object",
1613
+ compatibility: ["browser", "nodejs"],
1614
+ fn: isObject
1615
+ },
1616
+ {
1617
+ name: "JSONparse",
1618
+ category: "object",
1619
+ compatibility: ["browser", "nodejs"],
1620
+ fn: JSONparse
1621
+ },
1622
+ {
1623
+ name: "JSONstringify",
1624
+ category: "object",
1625
+ compatibility: ["browser", "nodejs"],
1626
+ fn: JSONstringify
1627
+ },
1628
+ {
1629
+ name: "merge",
1630
+ category: "object",
1631
+ compatibility: ["browser", "nodejs"],
1632
+ fn: merge
1633
+ },
1634
+ {
1635
+ name: "parseJSON",
1636
+ category: "object",
1637
+ compatibility: ["browser", "nodejs"],
1638
+ fn: parseJSON
1639
+ },
1640
+ {
1641
+ name: "pick",
1642
+ category: "object",
1643
+ compatibility: ["browser", "nodejs"],
1644
+ fn: pick
1645
+ },
1646
+ {
1647
+ name: "stringify",
1648
+ category: "object",
1649
+ compatibility: ["browser", "nodejs"],
1650
+ fn: stringify
1651
+ }
1652
+ ];
1653
+
1654
+ // src/helpers/path.ts
1655
+ import path5 from "path";
1656
+ var expectedType = (variableName, expectedType2, variableValue) => {
1657
+ const actualType = Object.prototype.toString.call(variableValue).slice(8, -1).toLowerCase();
1658
+ return `Expected ${variableName} to be of type ${expectedType2}, but got ${actualType}`;
1659
+ };
1660
+ var assertString = (name, value) => {
1661
+ if (typeof value !== "string") {
1662
+ throw new TypeError(expectedType(name, "string", value));
1663
+ }
1664
+ return value;
1665
+ };
1666
+ var absolute = function(filepath, options) {
1667
+ const fp = assertString("filepath", filepath);
1668
+ const cwd = options?.data?.root?.cwd ?? this?.cwd ?? process.cwd();
1669
+ return path5.resolve(cwd, fp);
1670
+ };
1671
+ var dirname = (filepath) => {
1672
+ const fp = assertString("filepath", filepath);
1673
+ return path5.dirname(fp);
1674
+ };
1675
+ var relative = (a, b) => {
1676
+ const from = assertString("first path", a);
1677
+ const to = assertString("second path", b);
1678
+ return path5.relative(path5.dirname(from), to);
1679
+ };
1680
+ var basename = (filepath) => {
1681
+ const fp = assertString("filepath", filepath);
1682
+ return path5.basename(fp);
1683
+ };
1684
+ var stem = (filepath) => {
1685
+ const fp = assertString("filepath", filepath);
1686
+ return path5.basename(fp, path5.extname(fp));
1687
+ };
1688
+ var extname = (filepath) => {
1689
+ const fp = assertString("filepath", filepath);
1690
+ return path5.extname(fp);
1691
+ };
1692
+ var resolveFn = function(filepath, ...paths) {
1693
+ let options;
1694
+ const last2 = paths[paths.length - 1];
1695
+ if (typeof last2 === "object" && last2 && "data" in last2) {
1696
+ options = paths.pop();
1697
+ }
1698
+ const cwd = options?.data?.root?.cwd ?? this?.cwd ?? process.cwd();
1699
+ const all2 = [
1700
+ cwd,
1701
+ assertString("filepath", filepath),
1702
+ ...paths.map((p, i) => assertString(`path${i}`, p))
1703
+ ];
1704
+ return path5.resolve(...all2);
1705
+ };
1706
+ var segments = (filepath, a, b) => {
1707
+ const fp = assertString("filepath", filepath);
1708
+ const start = Number(a);
1709
+ const end = Number(b);
1710
+ const segmentsArr = fp.split(/[\\/]+/);
1711
+ return segmentsArr.slice(start, end).join("/");
1712
+ };
1713
+ var helpers17 = [
1714
+ {
1715
+ name: "absolute",
1716
+ category: "path",
1717
+ compatibility: ["nodejs"],
1718
+ fn: absolute
1719
+ },
1720
+ {
1721
+ name: "dirname",
1722
+ category: "path",
1723
+ compatibility: ["nodejs"],
1724
+ fn: dirname
1725
+ },
1726
+ {
1727
+ name: "relative",
1728
+ category: "path",
1729
+ compatibility: ["nodejs"],
1730
+ fn: relative
1731
+ },
1732
+ {
1733
+ name: "basename",
1734
+ category: "path",
1735
+ compatibility: ["nodejs"],
1736
+ fn: basename
1737
+ },
1738
+ {
1739
+ name: "stem",
1740
+ category: "path",
1741
+ compatibility: ["nodejs"],
1742
+ fn: stem
1743
+ },
1744
+ {
1745
+ name: "extname",
1746
+ category: "path",
1747
+ compatibility: ["nodejs"],
1748
+ fn: extname
1749
+ },
1750
+ {
1751
+ name: "resolve",
1752
+ category: "path",
1753
+ compatibility: ["nodejs"],
1754
+ fn: resolveFn
1755
+ },
1756
+ {
1757
+ name: "segments",
1758
+ category: "path",
1759
+ compatibility: ["nodejs"],
1760
+ fn: segments
1761
+ }
1762
+ ];
1763
+
1764
+ // src/helpers/regex.ts
1765
+ import util2 from "handlebars-utils";
1766
+ var toRegex = (str, locals, options) => {
1767
+ const opts = util2.options({}, locals, options);
1768
+ return new RegExp(str, opts.flags);
1769
+ };
1770
+ var test = (str, regex) => {
1771
+ if (typeof str !== "string") {
1772
+ return false;
1773
+ }
1774
+ if (!(regex instanceof RegExp)) {
1775
+ throw new TypeError("expected a regular expression");
1776
+ }
1777
+ return regex.test(str);
1778
+ };
1779
+ var helpers18 = [
1780
+ {
1781
+ name: "toRegex",
1782
+ category: "regex",
1783
+ compatibility: ["browser", "nodejs"],
1784
+ fn: toRegex
1785
+ },
1786
+ {
1787
+ name: "test",
1788
+ category: "regex",
1789
+ compatibility: ["browser", "nodejs"],
1790
+ fn: test
1791
+ }
1792
+ ];
1793
+
1794
+ // src/helpers/string.ts
1795
+ var chop = (str) => str.trim().replace(/^[-_.\W\s]+|[-_.\W\s]+$/g, "");
1796
+ var changecase = (str, fn) => {
1797
+ if (str.length === 1) return str.toLowerCase();
1798
+ const res = chop(str).toLowerCase();
1799
+ return res.replace(/[-_.\W\s]+(\w|$)/g, (_, ch) => fn(ch));
1800
+ };
1801
+ var append = (str, suffix) => {
1802
+ if (typeof str === "string" && typeof suffix === "string") {
1803
+ return str + suffix;
1804
+ }
1805
+ return str;
1806
+ };
1807
+ var camelcase = (str) => typeof str === "string" ? changecase(str, (ch) => ch.toUpperCase()) : "";
1808
+ var capitalize = (str) => {
1809
+ if (typeof str !== "string" || str.length === 0) return "";
1810
+ return str.charAt(0).toUpperCase() + str.slice(1);
1811
+ };
1812
+ var capitalizeAll = (str) => {
1813
+ if (typeof str !== "string") return "";
1814
+ return str.replace(/\w\S*/g, (word) => capitalize(word));
1815
+ };
1816
+ var center = (str, spaces) => {
1817
+ if (typeof str !== "string") return "";
1818
+ let space = "";
1819
+ for (let i = 0; i < spaces; i++) {
1820
+ space += "&nbsp;";
1821
+ }
1822
+ return space + str + space;
1823
+ };
1824
+ var chopStr = (str) => typeof str === "string" ? chop(str) : "";
1825
+ var dashcase = (str) => typeof str === "string" ? changecase(str, (ch) => `-${ch}`) : "";
1826
+ var dotcase = (str) => typeof str === "string" ? changecase(str, (ch) => `.${ch}`) : "";
1827
+ var truncate = (str, limit, suffix) => {
1828
+ if (typeof str === "string") {
1829
+ if (typeof suffix !== "string") {
1830
+ suffix = "";
1831
+ }
1832
+ if (str.length > limit) {
1833
+ return str.slice(0, limit - suffix.length) + suffix;
1834
+ }
1835
+ return str;
1836
+ }
1837
+ return "";
1838
+ };
1839
+ var ellipsis = (str, limit) => {
1840
+ if (typeof str === "string") {
1841
+ if (str.length <= limit) {
1842
+ return str;
1843
+ }
1844
+ return `${truncate(str, limit)}\u2026`;
1845
+ }
1846
+ return "";
1847
+ };
1848
+ var hyphenate = (str) => typeof str === "string" ? str.split(" ").join("-") : "";
1849
+ var isString = (value) => typeof value === "string";
1850
+ var lowercase = (str) => {
1851
+ if (typeof str === "object" && str !== null && "fn" in str && typeof str.fn === "function") {
1852
+ return String(str.fn()).toLowerCase();
1853
+ }
1854
+ if (typeof str !== "string") return "";
1855
+ return str.toLowerCase();
1856
+ };
1857
+ var downcase = (str) => lowercase(str);
1858
+ var occurrences = (str, substring) => {
1859
+ if (typeof str !== "string") return "";
1860
+ const len = substring.length;
1861
+ let pos = str.indexOf(substring, 0);
1862
+ let n = 0;
1863
+ while (pos > -1) {
1864
+ n++;
1865
+ pos = str.indexOf(substring, pos + len);
1866
+ }
1867
+ return n;
1868
+ };
1869
+ var pascalcase = (str) => {
1870
+ if (typeof str !== "string") return "";
1871
+ const res = changecase(str, (ch) => ch.toUpperCase());
1872
+ return res.charAt(0).toUpperCase() + res.slice(1);
1873
+ };
1874
+ var pathcase = (str) => typeof str === "string" ? changecase(str, (ch) => `/${ch}`) : "";
1875
+ var plusify = (str, ch) => {
1876
+ if (typeof str !== "string") return "";
1877
+ if (typeof ch !== "string") ch = " ";
1878
+ return str.split(ch).join("+");
1879
+ };
1880
+ var prepend = (str, prefix) => {
1881
+ return typeof str === "string" && typeof prefix === "string" ? prefix + str : str;
1882
+ };
1883
+ var remove = (str, ch) => {
1884
+ if (typeof str !== "string") return "";
1885
+ if (typeof ch !== "string") return str;
1886
+ return str.split(ch).join("");
1887
+ };
1888
+ var removeFirst = (str, ch) => {
1889
+ if (typeof str !== "string") return "";
1890
+ if (typeof ch !== "string") return str;
1891
+ return str.replace(ch, "");
1892
+ };
1893
+ var replace = (str, a, b) => {
1894
+ if (typeof str !== "string") return "";
1895
+ if (typeof a !== "string") return str;
1896
+ if (typeof b !== "string") b = "";
1897
+ return str.split(a).join(b);
1898
+ };
1899
+ var replaceFirst = (str, a, b) => {
1900
+ if (typeof str !== "string") return "";
1901
+ if (typeof a !== "string") return str;
1902
+ if (typeof b !== "string") b = "";
1903
+ return str.replace(a, b);
1904
+ };
1905
+ var reverse = (str) => typeof str === "string" ? str.split("").reverse().join("") : "";
1906
+ var sentence = (str) => {
1907
+ if (typeof str !== "string") return "";
1908
+ return str.replace(
1909
+ /((?:\S[^.?!]*)[.?!]*)/g,
1910
+ (txt) => txt.charAt(0).toUpperCase() + txt.substr(1).toLowerCase()
1911
+ );
1912
+ };
1913
+ var snakecase = (str) => typeof str === "string" ? changecase(str, (ch) => `_${ch}`) : "";
1914
+ var trim = (str) => typeof str === "string" ? str.trim() : "";
1915
+ var trimLeft = (str) => typeof str === "string" ? str.replace(/^\s+/, "") : "";
1916
+ var trimRight = (str) => typeof str === "string" ? str.replace(/\s+$/, "") : "";
1917
+ var truncateWords = (str, count, suffix) => {
1918
+ if (typeof str === "string" && typeof count === "number" && Number.isFinite(count)) {
1919
+ if (typeof suffix !== "string") {
1920
+ suffix = "...";
1921
+ }
1922
+ const num = Math.trunc(count);
1923
+ let arr = str.split(" ");
1924
+ if (num < arr.length) {
1925
+ arr = arr.slice(0, num);
1926
+ }
1927
+ const val = arr.join(" ").trim();
1928
+ return val + suffix;
1929
+ }
1930
+ return "";
1931
+ };
1932
+ var truncateWordsAlias = truncateWords;
1933
+ var uppercase = (str) => {
1934
+ if (typeof str === "object" && str !== null && "fn" in str && typeof str.fn === "function") {
1935
+ return String(str.fn()).toUpperCase();
1936
+ }
1937
+ if (typeof str !== "string") return "";
1938
+ return str.toUpperCase();
1939
+ };
1940
+ var upcase = (str) => uppercase(str);
1941
+ var helpers19 = [
1942
+ {
1943
+ name: "append",
1944
+ category: "string",
1945
+ compatibility: ["browser", "nodejs"],
1946
+ fn: append
1947
+ },
1948
+ {
1949
+ name: "camelcase",
1950
+ category: "string",
1951
+ compatibility: ["browser", "nodejs"],
1952
+ fn: camelcase
1953
+ },
1954
+ {
1955
+ name: "capitalize",
1956
+ category: "string",
1957
+ compatibility: ["browser", "nodejs"],
1958
+ fn: capitalize
1959
+ },
1960
+ {
1961
+ name: "capitalizeAll",
1962
+ category: "string",
1963
+ compatibility: ["browser", "nodejs"],
1964
+ fn: capitalizeAll
1965
+ },
1966
+ {
1967
+ name: "center",
1968
+ category: "string",
1969
+ compatibility: ["browser", "nodejs"],
1970
+ fn: center
1971
+ },
1972
+ {
1973
+ name: "chop",
1974
+ category: "string",
1975
+ compatibility: ["browser", "nodejs"],
1976
+ fn: chopStr
1977
+ },
1978
+ {
1979
+ name: "dashcase",
1980
+ category: "string",
1981
+ compatibility: ["browser", "nodejs"],
1982
+ fn: dashcase
1983
+ },
1984
+ {
1985
+ name: "dotcase",
1986
+ category: "string",
1987
+ compatibility: ["browser", "nodejs"],
1988
+ fn: dotcase
1989
+ },
1990
+ {
1991
+ name: "ellipsis",
1992
+ category: "string",
1993
+ compatibility: ["browser", "nodejs"],
1994
+ fn: ellipsis
1995
+ },
1996
+ {
1997
+ name: "hyphenate",
1998
+ category: "string",
1999
+ compatibility: ["browser", "nodejs"],
2000
+ fn: hyphenate
2001
+ },
2002
+ {
2003
+ name: "isString",
2004
+ category: "string",
2005
+ compatibility: ["browser", "nodejs"],
2006
+ fn: isString
2007
+ },
2008
+ {
2009
+ name: "lowercase",
2010
+ category: "string",
2011
+ compatibility: ["browser", "nodejs"],
2012
+ fn: lowercase
2013
+ },
2014
+ {
2015
+ name: "downcase",
2016
+ category: "string",
2017
+ compatibility: ["browser", "nodejs"],
2018
+ fn: downcase
2019
+ },
2020
+ {
2021
+ name: "occurrences",
2022
+ category: "string",
2023
+ compatibility: ["browser", "nodejs"],
2024
+ fn: occurrences
2025
+ },
2026
+ {
2027
+ name: "pascalcase",
2028
+ category: "string",
2029
+ compatibility: ["browser", "nodejs"],
2030
+ fn: pascalcase
2031
+ },
2032
+ {
2033
+ name: "pathcase",
2034
+ category: "string",
2035
+ compatibility: ["browser", "nodejs"],
2036
+ fn: pathcase
2037
+ },
2038
+ {
2039
+ name: "plusify",
2040
+ category: "string",
2041
+ compatibility: ["browser", "nodejs"],
2042
+ fn: plusify
2043
+ },
2044
+ {
2045
+ name: "prepend",
2046
+ category: "string",
2047
+ compatibility: ["browser", "nodejs"],
2048
+ fn: prepend
2049
+ },
2050
+ {
2051
+ name: "remove",
2052
+ category: "string",
2053
+ compatibility: ["browser", "nodejs"],
2054
+ fn: remove
2055
+ },
2056
+ {
2057
+ name: "removeFirst",
2058
+ category: "string",
2059
+ compatibility: ["browser", "nodejs"],
2060
+ fn: removeFirst
2061
+ },
2062
+ {
2063
+ name: "replace",
2064
+ category: "string",
2065
+ compatibility: ["browser", "nodejs"],
2066
+ fn: replace
2067
+ },
2068
+ {
2069
+ name: "replaceFirst",
2070
+ category: "string",
2071
+ compatibility: ["browser", "nodejs"],
2072
+ fn: replaceFirst
2073
+ },
2074
+ {
2075
+ name: "reverse",
2076
+ category: "string",
2077
+ compatibility: ["browser", "nodejs"],
2078
+ fn: reverse
2079
+ },
2080
+ {
2081
+ name: "sentence",
2082
+ category: "string",
2083
+ compatibility: ["browser", "nodejs"],
2084
+ fn: sentence
2085
+ },
2086
+ {
2087
+ name: "snakecase",
2088
+ category: "string",
2089
+ compatibility: ["browser", "nodejs"],
2090
+ fn: snakecase
2091
+ },
2092
+ {
2093
+ name: "trim",
2094
+ category: "string",
2095
+ compatibility: ["browser", "nodejs"],
2096
+ fn: trim
2097
+ },
2098
+ {
2099
+ name: "trimLeft",
2100
+ category: "string",
2101
+ compatibility: ["browser", "nodejs"],
2102
+ fn: trimLeft
2103
+ },
2104
+ {
2105
+ name: "trimRight",
2106
+ category: "string",
2107
+ compatibility: ["browser", "nodejs"],
2108
+ fn: trimRight
2109
+ },
2110
+ {
2111
+ name: "truncate",
2112
+ category: "string",
2113
+ compatibility: ["browser", "nodejs"],
2114
+ fn: truncate
2115
+ },
2116
+ {
2117
+ name: "truncateWords",
2118
+ category: "string",
2119
+ compatibility: ["browser", "nodejs"],
2120
+ fn: truncateWordsAlias
2121
+ },
2122
+ {
2123
+ name: "uppercase",
2124
+ category: "string",
2125
+ compatibility: ["browser", "nodejs"],
2126
+ fn: uppercase
2127
+ },
2128
+ {
2129
+ name: "upcase",
2130
+ category: "string",
2131
+ compatibility: ["browser", "nodejs"],
2132
+ fn: upcase
2133
+ }
2134
+ ];
2135
+
2136
+ // src/helpers/url.ts
2137
+ import { escape as qsEscape } from "querystring";
2138
+ import { format, parse, resolve } from "url";
2139
+ var all = ["browser", "nodejs"];
2140
+ var encodeUri = (str) => {
2141
+ if (typeof str === "string") {
2142
+ return encodeURIComponent(str);
2143
+ }
2144
+ };
2145
+ var escapeFn = (str) => {
2146
+ if (typeof str === "string") {
2147
+ return qsEscape(str);
2148
+ }
2149
+ };
2150
+ var decodeUri = (str) => {
2151
+ if (typeof str === "string") {
2152
+ return decodeURIComponent(str);
2153
+ }
2154
+ };
2155
+ function urlEncode(...args) {
2156
+ return encodeUri.apply(this, args);
2157
+ }
2158
+ function urlDecode(...args) {
2159
+ return decodeUri.apply(this, args);
2160
+ }
2161
+ var urlResolve = (base, href) => resolve(String(base), String(href));
2162
+ var urlParse = (str) => parse(String(str));
2163
+ var stripQuerystring = (str) => {
2164
+ if (typeof str === "string") {
2165
+ return str.split("?")[0];
2166
+ }
2167
+ };
2168
+ var stripProtocol = (str) => {
2169
+ if (typeof str === "string") {
2170
+ const parsed = parse(str);
2171
+ parsed.protocol = "";
2172
+ return format(parsed);
2173
+ }
2174
+ };
2175
+ var helpers20 = [
2176
+ {
2177
+ name: "encodeURI",
2178
+ category: "url",
2179
+ compatibility: all,
2180
+ fn: encodeUri
2181
+ },
2182
+ {
2183
+ name: "escape",
2184
+ category: "url",
2185
+ compatibility: ["nodejs"],
2186
+ fn: escapeFn
2187
+ },
2188
+ {
2189
+ name: "decodeURI",
2190
+ category: "url",
2191
+ compatibility: all,
2192
+ fn: decodeUri
2193
+ },
2194
+ {
2195
+ name: "url_encode",
2196
+ category: "url",
2197
+ compatibility: all,
2198
+ fn: urlEncode
2199
+ },
2200
+ {
2201
+ name: "url_decode",
2202
+ category: "url",
2203
+ compatibility: all,
2204
+ fn: urlDecode
2205
+ },
2206
+ {
2207
+ name: "urlResolve",
2208
+ category: "url",
2209
+ compatibility: ["nodejs"],
2210
+ fn: urlResolve
2211
+ },
2212
+ {
2213
+ name: "urlParse",
2214
+ category: "url",
2215
+ compatibility: ["nodejs"],
2216
+ fn: urlParse
2217
+ },
2218
+ {
2219
+ name: "stripQuerystring",
2220
+ category: "url",
2221
+ compatibility: all,
2222
+ fn: stripQuerystring
2223
+ },
2224
+ {
2225
+ name: "stripProtocol",
2226
+ category: "url",
2227
+ compatibility: ["nodejs"],
2228
+ fn: stripProtocol
2229
+ }
2230
+ ];
2231
+
2232
+ // src/helper-registry.ts
2233
+ var HelperRegistry = class {
2234
+ _helpers = [];
2235
+ constructor() {
2236
+ this.init();
2237
+ }
2238
+ /**
2239
+ * Get all registered helpers.
2240
+ * @returns {Helper[]} The array of registered helpers.
2241
+ */
2242
+ get helpers() {
2243
+ return this._helpers;
2244
+ }
2245
+ /**
2246
+ * Initialize the helper registry. This is performed during the construction of the registry such as new HelperRegistry().
2247
+ */
2248
+ init() {
2249
+ this.registerHelpers(helpers);
2250
+ this.registerHelpers(helpers3);
2251
+ this.registerHelpers(helpers5);
2252
+ this.registerHelpers(helpers6);
2253
+ this.registerHelpers(helpers2);
2254
+ this.registerHelpers(helpers13);
2255
+ this.registerHelpers(helpers7);
2256
+ this.registerHelpers(helpers4);
2257
+ this.registerHelpers(helpers8);
2258
+ this.registerHelpers(helpers9);
2259
+ this.registerHelpers(helpers10);
2260
+ this.registerHelpers(helpers11);
2261
+ this.registerHelpers(helpers12);
2262
+ this.registerHelpers(helpers14);
2263
+ this.registerHelpers(helpers15);
2264
+ this.registerHelpers(helpers17);
2265
+ this.registerHelpers(helpers18);
2266
+ this.registerHelpers(helpers19);
2267
+ this.registerHelpers(helpers20);
2268
+ this.registerHelpers(helpers16);
2269
+ }
2270
+ /**
2271
+ * Register a helper.
2272
+ * @param {Helper} helper The helper to register.
2273
+ * @returns True if the helper was registered, false otherwise.
2274
+ */
2275
+ register(helper) {
2276
+ const result = false;
2277
+ if (!this.has(helper.name)) {
2278
+ this._helpers.push(helper);
2279
+ }
2280
+ return result;
2281
+ }
2282
+ /**
2283
+ * Register multiple helpers.
2284
+ * @param {Helper[]} helpers The array of helpers to register.
2285
+ */
2286
+ registerHelpers(helpers22) {
2287
+ for (const helper of helpers22) {
2288
+ this.register(helper);
2289
+ }
2290
+ }
2291
+ /**
2292
+ * Check if a helper is registered.
2293
+ * @param name The name of the helper.
2294
+ * @returns True if the helper is registered, false otherwise.
2295
+ */
2296
+ has(name) {
2297
+ return this._helpers.some((helper) => helper.name === name);
2298
+ }
2299
+ /**
2300
+ * Filter helpers by the given criteria.
2301
+ * @param filter The filter criteria.
2302
+ * @returns The filtered helpers.
2303
+ */
2304
+ filter(filter) {
2305
+ let result = this._helpers;
2306
+ if (filter.names) {
2307
+ result = result.filter((helper) => filter.names?.includes(helper.name));
2308
+ }
2309
+ if (filter.categories) {
2310
+ result = result.filter(
2311
+ (helper) => filter.categories?.includes(helper.category)
2312
+ );
2313
+ }
2314
+ if (filter.compatibility) {
2315
+ result = result.filter(
2316
+ (helper) => helper.compatibility?.some((c) => filter.compatibility?.includes(c))
2317
+ );
2318
+ }
2319
+ return result;
2320
+ }
2321
+ /**
2322
+ * Load Handlebars helpers.
2323
+ * @param {Handlebars} handlebars The Handlebars instance.
2324
+ * @returns {void}
2325
+ */
2326
+ load(handlebars2, filters) {
2327
+ let helpers22 = this._helpers;
2328
+ if (filters) {
2329
+ helpers22 = this.filter(filters);
2330
+ }
2331
+ for (const helper of helpers22) {
2332
+ handlebars2.registerHelper(helper.name, helper.fn);
2333
+ }
2334
+ }
2335
+ /**
2336
+ * Swap Handlebars helpers. This is used when you want to swap out legacy helpers for fumanchu helpers.
2337
+ * @param handlebars The Handlebars instance.
2338
+ * @returns {void}
2339
+ */
2340
+ swap(handlebars2) {
2341
+ for (const helper of this._helpers) {
2342
+ handlebars2.unregisterHelper(helper.name);
2343
+ handlebars2.registerHelper(helper.name, helper.fn);
2344
+ }
2345
+ }
2346
+ };
2347
+
2348
+ // src/index.ts
2349
+ var Handlebars3 = HandlebarsLib;
2350
+ var handlebars = HandlebarsLib.create();
2351
+ function helpers21(options) {
2352
+ const registry = new HelperRegistry();
2353
+ registry.load(options.handlebars ?? options.hbs);
2354
+ }
2355
+ async function createHandlebars() {
2356
+ const registry = new HelperRegistry();
2357
+ const handlebars2 = HandlebarsLib.create();
2358
+ if (Object.keys(HandlebarsLib.partials).length > 0) {
2359
+ handlebars2.registerPartial(HandlebarsLib.partials);
2360
+ }
2361
+ registry.load(handlebars2);
2362
+ if (process.env.NODE_ENV === "development") {
2363
+ console.warn(
2364
+ "createHandlebars will be deprecated in future versions, use `fumanchu` instead."
2365
+ );
2366
+ }
2367
+ return handlebars2;
2368
+ }
2369
+ function fumanchu(options) {
2370
+ const registry = new HelperRegistry();
2371
+ let handlebars2 = HandlebarsLib.create();
2372
+ if (options?.handlebars) {
2373
+ handlebars2 = options.handlebars;
2374
+ } else if (Object.keys(HandlebarsLib.partials).length > 0) {
2375
+ handlebars2.registerPartial(HandlebarsLib.partials);
2376
+ }
2377
+ registry.load(handlebars2);
2378
+ return handlebars2;
2379
+ }
2380
+ export {
2381
+ Handlebars3 as Handlebars,
2382
+ HelperRegistry,
2383
+ createHandlebars,
2384
+ fumanchu,
2385
+ handlebars,
2386
+ helpers21 as helpers
2387
+ };
2388
+ /* c8 ignore next -- @preserve */