Merge branch 'docsify'
This commit is contained in:
commit
1701283e11
@ -12,4 +12,4 @@ declare the updates you would like to make and it will take care of the rest. It
|
||||
will recursively return the same instance if no changes have been made, making
|
||||
it ideal for using reference equality checks to detect changes.
|
||||
|
||||
Full documentation can be found at [https://yanick.github.com/updeep-remeda](https://yanick.github.com/updeep-remeda).
|
||||
Full documentation can be found at [https://yanick.github.com/updeep-remeda/index.html](https://yanick.github.com/updeep-remeda/index.html).
|
||||
|
Binary file not shown.
Binary file not shown.
@ -1 +0,0 @@
|
||||
div.svelte-ns3bhs{background:lightgreen;margin:0 2em;padding:.25em 1em;font-weight:400;border-radius:1em;color:#000}h4.svelte-ns3bhs{margin:0}
|
Binary file not shown.
Binary file not shown.
File diff suppressed because one or more lines are too long
@ -1 +0,0 @@
|
||||
import{_ as r}from"./_layout-32f74dae.js";import{default as t}from"../components/pages/_layout.svelte-ac40f340.js";export{t as component,r as universal};
|
@ -1 +0,0 @@
|
||||
import{default as t}from"../components/error.svelte-884b4aac.js";export{t as component};
|
@ -1 +0,0 @@
|
||||
import{_ as e}from"./_page-a27df1e4.js";export{e as universal};
|
@ -1 +0,0 @@
|
||||
import{_ as e}from"./_page-115bdbbb.js";export{e as universal};
|
@ -1 +0,0 @@
|
||||
import{default as t}from"../components/pages/latest/api/_page.md-bd91dac8.js";export{t as component};
|
@ -1 +0,0 @@
|
||||
import{default as t}from"../components/pages/latest/get-started/_page.md-5c5fe5e6.js";export{t as component};
|
@ -1,9 +0,0 @@
|
||||
import{S as R,i as j,s as q,R as A,$ as ve,a0 as pe,m as k,h as d,a1 as K,b as E,_ as re,a2 as U,T as Z,k as w,a as D,l as C,c as S,n as b,p as z,W as v,f as L,g as ce,t as N,d as fe,ac as be,q as H,r as V,u as P,w as ye,x as ke,y as we,O as Ce,z as Ee,ao as Ie,e as x,U as ue,V as $,X as he,Y as de,Z as _e,Q as ee}from"./singletons-79165f10.js";import{c as T,g as Le}from"./contexts-c54c563b.js";function He(o){let e,t='<path fill="currentColor" d="M7 6V3a1 1 0 0 1 1-1h12a1 1 0 0 1 1 1v14a1 1 0 0 1-1 1h-3v3c0 .552-.45 1-1.007 1H4.007A1.001 1.001 0 0 1 3 21l.003-14c0-.552.45-1 1.007-1H7zM5.003 8L5 20h10V8H5.003zM9 6h8v10h2V4H9v2z"/>',l=[{viewBox:"0 0 24 24"},{width:"1.2em"},{height:"1.2em"},o[0]],i={};for(let a=0;a<l.length;a+=1)i=A(i,l[a]);return{c(){e=ve("svg"),this.h()},l(a){e=pe(a,"svg",{viewBox:!0,width:!0,height:!0});var s=k(e);s.forEach(d),this.h()},h(){K(e,i)},m(a,s){E(a,e,s),e.innerHTML=t},p(a,[s]){K(e,i=re(l,[{viewBox:"0 0 24 24"},{width:"1.2em"},{height:"1.2em"},s&1&&a[0]]))},i:U,o:U,d(a){a&&d(e)}}}function Ve(o,e,t){return o.$$set=l=>{t(0,e=A(A({},e),Z(l)))},e=Z(e),[e]}class Te extends R{constructor(e){super(),j(this,e,Ve,He,q,{})}}function te(o,e,t){const l=o.slice();return l[24]=e[t],l}function le(o){let e,t,l,i,a,s=o[7]&&ie(o),n=o[4]&&ne(o);return{c(){e=w("div"),s&&s.c(),t=D(),l=w("div"),i=D(),n&&n.c(),this.h()},l(r){e=C(r,"DIV",{class:!0,style:!0});var c=k(e);s&&s.l(c),t=S(c),l=C(c,"DIV",{class:!0}),k(l).forEach(d),i=S(c),n&&n.l(c),c.forEach(d),this.h()},h(){b(l,"class","flex-1"),b(e,"class","sticky top-0 left-0 z-10 flex items-center rounded-md pt-2 backdrop-blur supports-backdrop-blur:bg-white/60"),z(e,"background-color","var(--kd-code-fence-top-bar-bg)")},m(r,c){E(r,e,c),s&&s.m(e,null),v(e,t),v(e,l),v(e,i),n&&n.m(e,null),a=!0},p(r,c){r[7]?s?s.p(r,c):(s=ie(r),s.c(),s.m(e,t)):s&&(s.d(1),s=null),r[4]?n?(n.p(r,c),c&16&&L(n,1)):(n=ne(r),n.c(),L(n,1),n.m(e,null)):n&&(ce(),N(n,1,1,()=>{n=null}),fe())},i(r){a||(L(n),a=!0)},o(r){N(n),a=!1},d(r){r&&d(e),s&&s.d(),n&&n.d()}}}function ie(o){let e,t;return{c(){e=w("span"),t=H(o[6]),this.h()},l(l){e=C(l,"SPAN",{class:!0});var i=k(e);t=V(i,o[6]),i.forEach(d),this.h()},h(){b(e,"class","ml-3.5 font-mono text-sm text-gray-300")},m(l,i){E(l,e,i),v(e,t)},p(l,i){i&64&&P(t,l[6])},d(l){l&&d(e)}}}function ne(o){let e,t,l=o[11].code.copied+"",i,a,s,n,r,c,h=o[11].code.copy+"",m,_,u,p;return n=new Te({props:{width:"24",height:"24",class:T(o[5]?"opacity-0":"opacity-100 transition-opacity duration-600 ease-in")}}),{c(){e=w("button"),t=w("div"),i=H(l),s=D(),ye(n.$$.fragment),r=D(),c=w("span"),m=H(h),this.h()},l(g){e=C(g,"BUTTON",{type:!0,class:!0});var y=k(e);t=C(y,"DIV",{class:!0,"aria-hidden":!0,style:!0});var I=k(t);i=V(I,l),I.forEach(d),s=S(y),ke(n.$$.fragment,y),r=S(y),c=C(y,"SPAN",{class:!0});var O=k(c);m=V(O,h),O.forEach(d),y.forEach(d),this.h()},h(){b(t,"class",a=T("text-white absolute top-2.5 right-4 transition-opacity z-10 duration-300 px-2 py-1 rounded-md ease-out text-sm font-mono",o[5]?"opacity-100":"hidden opacity-0")),b(t,"aria-hidden","true"),z(t,"background-color","var(--kd-code-copied-bg-color)"),b(c,"class","sr-only"),b(e,"type","button"),b(e,"class","mr-2 px-2 py-1 hover:text-white")},m(g,y){E(g,e,y),v(e,t),v(t,i),v(e,s),we(n,e,null),v(e,r),v(e,c),v(c,m),_=!0,u||(p=Ce(e,"click",o[14]),u=!0)},p(g,y){(!_||y&2048)&&l!==(l=g[11].code.copied+"")&&P(i,l),(!_||y&32&&a!==(a=T("text-white absolute top-2.5 right-4 transition-opacity z-10 duration-300 px-2 py-1 rounded-md ease-out text-sm font-mono",g[5]?"opacity-100":"hidden opacity-0")))&&b(t,"class",a);const I={};y&32&&(I.class=T(g[5]?"opacity-0":"opacity-100 transition-opacity duration-600 ease-in")),n.$set(I),(!_||y&2048)&&h!==(h=g[11].code.copy+"")&&P(m,h)},i(g){_||(L(n.$$.fragment,g),_=!0)},o(g){N(n.$$.fragment,g),_=!1},d(g){g&&d(e),Ee(n),u=!1,p()}}}function se(o){let e,t,l,i=o[9].join(`
|
||||
`)+"",a,s;return{c(){e=w("pre"),t=H(" "),l=w("div"),a=H(i),s=H(`
|
||||
`),this.h()},l(n){e=C(n,"PRE",{class:!0,style:!0});var r=k(e);t=V(r," "),l=C(r,"DIV",{class:!0,"aria-hidden":!0});var c=k(l);a=V(c,i),c.forEach(d),s=V(r,`
|
||||
`),r.forEach(d),this.h()},h(){b(l,"class","hidden flex-none select-none text-right text-slate-600 992:block"),b(l,"aria-hidden","true"),b(e,"class","absolute top-3.5 left-0 m-0 flex flex-col text-sm leading-[27px]"),z(e,"background-color","transparent"),z(e,"border-radius","0"),z(e,"padding-top","0")},m(n,r){E(n,e,r),v(e,t),v(e,l),v(l,a),v(e,s)},p(n,r){r&512&&i!==(i=n[9].join(`
|
||||
`)+"")&&P(a,i)},d(n){n&&d(e)}}}function oe(o){let e,t=o[9],l=[];for(let i=0;i<t.length;i+=1)l[i]=ae(te(o,t,i));return{c(){e=w("div");for(let i=0;i<l.length;i+=1)l[i].c();this.h()},l(i){e=C(i,"DIV",{class:!0,"aria-hidden":!0});var a=k(e);for(let s=0;s<l.length;s+=1)l[s].l(a);a.forEach(d),this.h()},h(){b(e,"class","pointer-events-none absolute inset-0 mt-[0.7em] h-full w-full leading-[27px]"),b(e,"aria-hidden","true")},m(i,a){E(i,e,a);for(let s=0;s<l.length;s+=1)l[s].m(e,null)},p(i,a){if(a&9728){t=i[9];let s;for(s=0;s<t.length;s+=1){const n=te(i,t,s);l[s]?l[s].p(n,a):(l[s]=ae(n),l[s].c(),l[s].m(e,null))}for(;s<l.length;s+=1)l[s].d(1);l.length=t.length}},d(i){i&&d(e),Ie(l,i)}}}function De(o){let e;return{c(){e=w("br")},l(t){e=C(t,"BR",{})},m(t,l){E(t,e,l)},d(t){t&&d(e)}}}function Se(o){let e,t;return{c(){e=w("div"),t=H(`
|
||||
`),this.h()},l(l){e=C(l,"DIV",{class:!0,style:!0});var i=k(e);t=V(i,`
|
||||
`),i.forEach(d),this.h()},h(){b(e,"class","w-full border-l-[5px] font-mono text-transparent"),z(e,"border-color","var(--kd-code-highlight-border)"),z(e,"background-color","var(--kd-code-highlight-color)")},m(l,i){E(l,e,i),v(e,t)},d(l){l&&d(e)}}}function ae(o){let e,t;function l(s,n){return n&1536&&(e=null),e==null&&(e=!!s[13](s[24],s[10])),e?Se:De}let i=l(o,-1),a=i(o);return{c(){a.c(),t=x()},l(s){a.l(s),t=x()},m(s,n){a.m(s,n),E(s,t,n)},p(s,n){i!==(i=l(s,n))&&(a.d(1),a=i(s),a&&(a.c(),a.m(t.parentNode,t)))},d(s){a.d(s),s&&d(t)}}}function ze(o){let e,t,l,i,a,s,n,r,c,h=o[8]&&le(o),m=o[3]&&se(o),_=o[10].length>0&&oe(o);return{c(){e=w("div"),h&&h.c(),t=D(),l=w("div"),i=w("div"),s=D(),m&&m.c(),n=D(),_&&_.c(),this.h()},l(u){e=C(u,"DIV",{class:!0,style:!0});var p=k(e);h&&h.l(p),t=S(p),l=C(p,"DIV",{class:!0});var g=k(l);i=C(g,"DIV",{class:!0});var y=k(i);y.forEach(d),s=S(g),m&&m.l(g),n=S(g),_&&_.l(g),g.forEach(d),p.forEach(d),this.h()},h(){b(i,"class",a=T(o[3]&&"pl-10")),b(l,"class","code relative z-0 overflow-hidden"),b(e,"class",r=T("code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto","border border-gray-divider",o[0]&&`lang-${o[0]}`,o[1]&&`ext-${o[1]}`)),z(e,"background-color","var(--kd-code-fence-bg)")},m(u,p){E(u,e,p),h&&h.m(e,null),v(e,t),v(e,l),v(l,i),i.innerHTML=o[2],v(l,s),m&&m.m(l,null),v(l,n),_&&_.m(l,null),c=!0},p(u,[p]){u[8]?h?(h.p(u,p),p&256&&L(h,1)):(h=le(u),h.c(),L(h,1),h.m(e,t)):h&&(ce(),N(h,1,1,()=>{h=null}),fe()),(!c||p&4)&&(i.innerHTML=u[2]),(!c||p&8&&a!==(a=T(u[3]&&"pl-10")))&&b(i,"class",a),u[3]?m?m.p(u,p):(m=se(u),m.c(),m.m(l,n)):m&&(m.d(1),m=null),u[10].length>0?_?_.p(u,p):(_=oe(u),_.c(),_.m(l,null)):_&&(_.d(1),_=null),(!c||p&3&&r!==(r=T("code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto","border border-gray-divider",u[0]&&`lang-${u[0]}`,u[1]&&`ext-${u[1]}`)))&&b(e,"class",r)},i(u){c||(L(h),c=!0)},o(u){N(h),c=!1},d(u){u&&d(e),h&&h.d(),m&&m.d(),_&&_.d()}}}function Ne(o,e,t){let l,i,a,s,n,r,c,{lang:h=null}=e,{ext:m=null}=e,{code:_=null}=e,{rawCode:u=null}=e,{title:p=null}=e,{linesCount:g=((_==null?void 0:_.match(/"line"/g))||[]).length}=e,{showLineNumbers:y=!1}=e,{highlightLines:I=[]}=e,{showCopyCode:O=!1}=e,{copyHighlightOnly:Q=!1}=e,{copySteps:B=!1}=e;const G=Le();be(o,G,f=>t(11,c=f));let M=1,W=[];const J=(f,X)=>l.some(([Y,ge])=>f>=Y&&f<=ge);let F=!1;async function me(){try{const f=l.length>0&&(Q||B)?a.split(`
|
||||
`).filter((X,Y)=>J(Y+1)).join(`
|
||||
`):a;await navigator.clipboard.writeText(f)}catch{}if(t(5,F=!0),B){const f=M+1,X=I.length>0?I.length:i.length;t(21,M=f>X?1:f)}}return o.$$set=f=>{"lang"in f&&t(0,h=f.lang),"ext"in f&&t(1,m=f.ext),"code"in f&&t(2,_=f.code),"rawCode"in f&&t(15,u=f.rawCode),"title"in f&&t(16,p=f.title),"linesCount"in f&&t(17,g=f.linesCount),"showLineNumbers"in f&&t(3,y=f.showLineNumbers),"highlightLines"in f&&t(18,I=f.highlightLines),"showCopyCode"in f&&t(4,O=f.showCopyCode),"copyHighlightOnly"in f&&t(19,Q=f.copyHighlightOnly),"copySteps"in f&&t(20,B=f.copySteps)},o.$$.update=()=>{o.$$.dirty&3407872&&B&&t(22,W=[I[M-1]??[M,M]]),o.$$.dirty&5505024&&t(10,l=B?W:I),o.$$.dirty&131072&&t(9,i=[...Array(g-1).keys()].map(f=>f+1)),o.$$.dirty&32768&&(a=u==null?void 0:u.replace(/​/g,"")),o.$$.dirty&32&&F&&setTimeout(()=>{t(5,F=!1)},400),o.$$.dirty&65552&&t(8,s=p||O),o.$$.dirty&65538&&t(7,n=p||m),o.$$.dirty&65538&&t(6,r=p??(m==="sh"?"terminal":m))},[h,m,_,y,O,F,r,n,s,i,l,c,G,J,me,u,p,g,I,Q,B,M,W]}class Fe extends R{constructor(e){super(),j(this,e,Ne,ze,q,{lang:0,ext:1,code:2,rawCode:15,title:16,linesCount:17,showLineNumbers:3,highlightLines:18,showCopyCode:4,copyHighlightOnly:19,copySteps:20})}}function Oe(o){let e,t;return{c(){e=w("code"),t=H(o[0])},l(l){e=C(l,"CODE",{});var i=k(e);t=V(i,o[0]),i.forEach(d)},m(l,i){E(l,e,i),v(e,t)},p(l,[i]){i&1&&P(t,l[0])},i:U,o:U,d(l){l&&d(e)}}}function Be(o,e,t){let{code:l}=e;return o.$$set=i=>{"code"in i&&t(0,l=i.code)},[l]}class Ue extends R{constructor(e){super(),j(this,e,Be,Oe,q,{code:0})}}function Me(o){let e,t;const l=o[2].default,i=ue(l,o,o[1],null);let a=[o[0]],s={};for(let n=0;n<a.length;n+=1)s=A(s,a[n]);return{c(){e=w("a"),i&&i.c(),this.h()},l(n){e=C(n,"A",{});var r=k(e);i&&i.l(r),r.forEach(d),this.h()},h(){$(e,s)},m(n,r){E(n,e,r),i&&i.m(e,null),t=!0},p(n,[r]){i&&i.p&&(!t||r&2)&&he(i,l,n,n[1],t?_e(l,n[1],r,null):de(n[1]),null),$(e,s=re(a,[r&1&&n[0]]))},i(n){t||(L(i,n),t=!0)},o(n){N(i,n),t=!1},d(n){n&&d(e),i&&i.d(n)}}}function Ae(o,e,t){const l=[];let i=ee(e,l),{$$slots:a={},$$scope:s}=e;return o.$$set=n=>{e=A(A({},e),Z(n)),t(0,i=ee(e,l)),"$$scope"in n&&t(1,s=n.$$scope)},[i,s,a]}class Qe extends R{constructor(e){super(),j(this,e,Ae,Me,q,{})}}function Pe(o){let e,t,l,i,a;const s=o[1].default,n=ue(s,o,o[0],null);return{c(){e=w("div"),t=w("h4"),l=H("💡 Info"),i=D(),n&&n.c(),this.h()},l(r){e=C(r,"DIV",{class:!0});var c=k(e);t=C(c,"H4",{class:!0});var h=k(t);l=V(h,"💡 Info"),h.forEach(d),i=S(c),n&&n.l(c),c.forEach(d),this.h()},h(){b(t,"class","svelte-ns3bhs"),b(e,"class","svelte-ns3bhs")},m(r,c){E(r,e,c),v(e,t),v(t,l),v(e,i),n&&n.m(e,null),a=!0},p(r,[c]){n&&n.p&&(!a||c&1)&&he(n,s,r,r[0],a?_e(s,r[0],c,null):de(r[0]),null)},i(r){a||(L(n,r),a=!0)},o(r){N(n,r),a=!1},d(r){r&&d(e),n&&n.d(r)}}}function Re(o,e,t){let{$$slots:l={},$$scope:i}=e;return o.$$set=a=>{"$$scope"in a&&t(0,i=a.$$scope)},[i,l]}class We extends R{constructor(e){super(),j(this,e,Re,Pe,q,{})}}export{Ue as C,We as I,Qe as L,Fe as a};
|
@ -1 +0,0 @@
|
||||
function o(t){return typeof t=="string"}function s(t){return u(t).replace(/\//g,"_")}function u(t){return t.replace(/^\//,"").replace(/\/$/,"")}async function l(t){const r=t.url.pathname;try{const e=`/kit-docs/${r==="/"?"index":s(r.replace(/\.html$/,""))}`;return await(await t.fetch(e+".meta")).json()}catch{return null}}async function i(t,r){const e=d(r.url,t);if(!e)return null;try{return(await r.fetch(`/kit-docs/${s(e)}.sidebar`)).json()}catch{return null}}function d(t,r){if(o(r))return r;const e=t.pathname,n=Object.keys(r).sort((a,c)=>c.length-a.length);for(const a of n)if(e.startsWith(a))return r[a];return null}function f(t={}){return async r=>{const e=await l(r);return{...t.sidebar?{meta:e,sidebar:await i(t.sidebar,r)}:{meta:e}}}}const h=!0,b=f({sidebar:{"/":null,"/docs":"/docs"}}),m=Object.freeze(Object.defineProperty({__proto__:null,load:b,prerender:h},Symbol.toStringTag,{value:"Module"}));export{m as _,b as l,h as p};
|
@ -1 +0,0 @@
|
||||
import{r as e}from"./index-35a671a5.js";const t=!0;async function r(){throw e(307,"/latest/get-started")}const a=Object.freeze(Object.defineProperty({__proto__:null,load:r,prerender:t},Symbol.toStringTag,{value:"Module"}));export{a as _,r as l,t as p};
|
@ -1 +0,0 @@
|
||||
import{r as e}from"./index-35a671a5.js";const t=!0;async function r(){throw e(307,"/latest/get-started")}const a=Object.freeze(Object.defineProperty({__proto__:null,load:r,prerender:t},Symbol.toStringTag,{value:"Module"}));export{a as _,r as l,t as p};
|
@ -1 +0,0 @@
|
||||
import{am as p,an as d,a8 as E,a9 as a}from"./singletons-79165f10.js";import{p as I}from"./stores-1c9d0b64.js";function D(t){return t===null}function F(t){return typeof t>"u"}function C(t){return typeof t=="string"}function j(t){return typeof t=="function"}function G(t){return t===window}function O(t){return t instanceof RegExp}function N(t){var n,s,e="";if(typeof t=="string"||typeof t=="number")e+=t;else if(typeof t=="object")if(Array.isArray(t))for(n=0;n<t.length;n++)t[n]&&(s=N(t[n]))&&(e&&(e+=" "),e+=s);else for(n in t)t[n]&&(e&&(e+=" "),e+=n);return e}function K(){for(var t,n,s=0,e="";s<arguments.length;)(t=arguments[s++])&&(n=N(t))&&(e&&(e+=" "),e+=n);return e}function _(t){return t.charAt(0).toUpperCase()+t.slice(1)}function x(t){return _((t==null?void 0:t.replace(/-./g,n=>" "+n[1].toUpperCase()))??"")}function v(t){return(t==null?void 0:t.replace(/\s/g,"-").toLowerCase())??""}const h=Symbol(""),X={canUpdateHash:()=>!0,cleanHash:t=>t};function Y(){try{return p(h)}catch(t){console.error(t),console.warn("[kit-docs]: attempted to get navigation context before setting it.")}}function M(t){d(h,t)}const T=Symbol("");function P(){try{return p(T)}catch(t){console.error(t),console.warn("[kit-docs]: attempted to get navbar context before setting it.")}}function V(t){d(T,t)}function w(t=null){var e;if(!t)return{links:{}};const n={},s=((e=t.baseUrl)==null?void 0:e.replace(/\/$/,""))??"";for(const i of Object.keys(t.links)){const u=t.links[i],g=v(i),l=C(t.links[i][0])?x(i):i;for(const c of u){const b=C(c)?{title:x(c),slug:`${s}/${g}/${c}`}:c;n[l]||(n[l]=[]),n[l].push(b)}}return{...t,links:n}}function R({match:t,slug:n},s){const e=s.replace(/\.html/,"");return t==="deep"?e===n||e.startsWith(n)&&e[n.length]==="/":O(t)?t.test(n):e===n}const k=Symbol();function W(t){const n=t&&"subscribe"in t?t:E(t),s=a(n,o=>w(o)),e=a(s,o=>Object.values(o.links).flat()),i=a([e,I],([o,r])=>o.findIndex(f=>R(f,r.url.pathname))),u=a([e,i],([o,r])=>o[r]),g=a([e,i],([o,r])=>o[r-1]),l=a([e,i],([o,r])=>o[r+1]),c=a([s,u],([o,r])=>{const f=Object.keys(o.links).find(A=>{var m;return(m=o.links[A])==null?void 0:m.some(y=>y.title===(r==null?void 0:r.title)&&y.slug===(r==null?void 0:r.slug))});return f!=="."?f:null});return{config:s,allLinks:e,activeLinkIndex:i,activeLink:u,previousLink:g,nextLink:l,activeCategory:c}}function z(t){d(k,t)}function B(){try{return p(k)}catch(t){console.error(t),console.warn("[kit-docs]: attempted to get sidebar context before setting it.")}}const H={nav:{previous:"Previous",next:"Next",mainMenu:"Main navigation menu",openSidebar:"Open main sidebar",options:"Options",links:"Links"},toc:{title:"On this page"},colorScheme:{title:"Color Scheme",light:"Light",dark:"Dark",system:"System",theme:"Theme"},dialog:{close:"Close dialog"},admonition:{note:"NOTE",info:"INFO",tip:"TIP",warning:"WARNING",danger:"DANGER",experimental:"EXPERIMENTAL"},code:{copy:"Copy code",copied:"Copied!"}},S=Symbol();function q(){try{return p(S)}catch(t){console.error(t),console.warn("[kit-docs]: attempted to get i18n context before setting it.")}}function J(t){d(S,t)}export{X as D,G as a,D as b,K as c,P as d,j as e,B as f,q as g,R as h,F as i,Y as j,V as k,z as l,W as m,J as n,H as o,M as s,_ as u};
|
@ -1 +0,0 @@
|
||||
class i{constructor(t,s){this.status=t,typeof s=="string"?this.body={message:s}:s?this.body=s:this.body={message:`Error: ${t}`}}toString(){return JSON.stringify(this.body)}}class e{constructor(t,s){this.status=t,this.location=s}}export{i as H,e as R};
|
@ -1 +0,0 @@
|
||||
import{R as t}from"./control-f5b05b5f.js";function n(r,e){return new t(r,e)}export{n as r};
|
File diff suppressed because one or more lines are too long
@ -1 +0,0 @@
|
||||
import{G as e}from"./singletons-79165f10.js";const r=()=>{const s=e;return{page:{subscribe:s.page.subscribe},navigating:{subscribe:s.navigating.subscribe},updated:s.updated}},b={subscribe(s){return r().page.subscribe(s)}};export{b as p};
|
@ -1 +0,0 @@
|
||||
import{S as x,i as S,s as g,k as _,q as h,a as k,l as d,m as v,r as b,h as m,c as y,b as f,W as E,u as $,a2 as q,ac as C}from"../chunks/singletons-79165f10.js";import{p as H}from"../chunks/stores-1c9d0b64.js";function P(n){var u;let a,t=n[0].status+"",r,o,l,i=((u=n[0].error)==null?void 0:u.message)+"",c;return{c(){a=_("h1"),r=h(t),o=k(),l=_("p"),c=h(i)},l(e){a=d(e,"H1",{});var s=v(a);r=b(s,t),s.forEach(m),o=y(e),l=d(e,"P",{});var p=v(l);c=b(p,i),p.forEach(m)},m(e,s){f(e,a,s),E(a,r),f(e,o,s),f(e,l,s),E(l,c)},p(e,[s]){var p;s&1&&t!==(t=e[0].status+"")&&$(r,t),s&1&&i!==(i=((p=e[0].error)==null?void 0:p.message)+"")&&$(c,i)},i:q,o:q,d(e){e&&m(a),e&&m(o),e&&m(l)}}}function W(n,a,t){let r;return C(n,H,o=>t(0,r=o)),[r]}class z extends x{constructor(a){super(),S(this,a,W,P,g,{})}}export{z as default};
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@ -1,78 +0,0 @@
|
||||
import{S as ln,i as pn,s as on,k as t,q as y,a as F,w as A,l as r,m as c,r as D,h as n,c as C,x as f,n as U,b as o,W as l,y as u,f as m,t as d,z as $,a2 as tn}from"../../../../chunks/singletons-79165f10.js";import{L as vs,I as rn,a as Gs,C as ss}from"../../../../chunks/Info-8cb253a1.js";function cn(b){let e;return{c(){e=y("#")},l(p){e=D(p,"#")},m(p,i){o(p,e,i)},d(p){p&&n(e)}}}function yn(b){let e,p,i,g,_;return i=new ss({props:{code:"updeep"}}),{c(){e=t("p"),p=y(`This is a fork of the main updeep package. For ease of reading — not to
|
||||
mention ease of shamelessly lifting large pieces of the original
|
||||
documentation — in this documentation all mentions of `),A(i.$$.fragment),g=y(` refers to this
|
||||
fork.`)},l(h){e=r(h,"P",{});var E=c(e);p=D(E,`This is a fork of the main updeep package. For ease of reading — not to
|
||||
mention ease of shamelessly lifting large pieces of the original
|
||||
documentation — in this documentation all mentions of `),f(i.$$.fragment,E),g=D(E,` refers to this
|
||||
fork.`),E.forEach(n)},m(h,E){o(h,e,E),l(e,p),u(i,e,null),l(e,g),_=!0},p:tn,i(h){_||(m(i.$$.fragment,h),_=!0)},o(h){d(i.$$.fragment,h),_=!1},d(h){h&&n(e),$(i)}}}function Dn(b){let e;return{c(){e=y("#")},l(p){e=D(p,"#")},m(p,i){o(p,e,i)},d(p){p&&n(e)}}}function Fn(b){let e;return{c(){e=y("#")},l(p){e=D(p,"#")},m(p,i){o(p,e,i)},d(p){p&&n(e)}}}function Cn(b){let e;return{c(){e=y("#")},l(p){e=D(p,"#")},m(p,i){o(p,e,i)},d(p){p&&n(e)}}}function An(b){let e,p,i,g,_,h,E,w,j,ks,Cs,P,As,J,ws,fs,V,qs,us,X,xs,ms,q,z,Is,ds,v,ns,as,js,Ps,es,ls,zs,Ts,ps,os,Ls,$s,O,T,ts,k,S,Rs,H,Bs,M,Us,Os,rs,L,N,Ss,K,Hs,hs,x,R,Ms,bs,Q,I,B,Ns,Es,W,gs;return j=new vs({props:{class:"header-anchor",href:"#about","aria-hidden":"true",$$slots:{default:[cn]},$$scope:{ctx:b}}}),P=new rn({props:{$$slots:{default:[yn]},$$scope:{ctx:b}}}),z=new vs({props:{class:"header-anchor",href:"#differences-with-the-original-updeep","aria-hidden":"true",$$slots:{default:[Dn]},$$scope:{ctx:b}}}),O=new Gs({props:{lang:"javascript",ext:"js",linesCount:10,code:`<pre><code><span class="line"><span style="color: #676E95">// original updeep</span></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> dataIn </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">a</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">b</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">2</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">let</span><span style="color: #A6ACCD"> dataOut </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">c</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> dataIn)</span><span style="color: #89DDFF">;</span><span style="color: #A6ACCD"> </span><span style="color: #676E95">// simple call</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">dataOut </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">c</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)(dataIn)</span><span style="color: #89DDFF">;</span><span style="color: #A6ACCD"> </span><span style="color: #676E95">// curried</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #676E95">// updeep-remeda</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">dataOut </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(dataIn</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">c</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span><span style="color: #A6ACCD"> </span><span style="color: #676E95">// simple call</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">dataOut </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">c</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)(dataIn)</span><span style="color: #89DDFF">;</span><span style="color: #A6ACCD"> </span><span style="color: #676E95">// curried</span></span>
|
||||
<span class="line"></span></code></pre>`}}),S=new ss({props:{code:"withDefault"}}),H=new ss({props:{code:"pipe"}}),M=new ss({props:{code:"??"}}),N=new ss({props:{code:"u.omitted"}}),K=new ss({props:{code:"u.skip"}}),R=new vs({props:{class:"header-anchor",href:"#installation","aria-hidden":"true",$$slots:{default:[Fn]},$$scope:{ctx:b}}}),Q=new Gs({props:{lang:"bash",ext:"sh",linesCount:4,code:`<pre><code><span class="line"><span style="color: #A6ACCD">$ npm install @yanick/updeep-remeda</span></span>
|
||||
<span class="line"><span style="color: #676E95"># or</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">$ pnpm install @yanick/updeep-remeda</span></span>
|
||||
<span class="line"></span></code></pre>`}}),B=new vs({props:{class:"header-anchor",href:"#full-example","aria-hidden":"true",$$slots:{default:[Cn]},$$scope:{ctx:b}}}),W=new Gs({props:{lang:"javascript",ext:"js",linesCount:42,code:`<pre><code><span class="line"><span style="color: #89DDFF">import</span><span style="color: #A6ACCD"> u </span><span style="color: #89DDFF">from</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">@yanick/updeep-remeda</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> person </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">first</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Bill</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">last</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Sagat</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">children</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Mary-Kate</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">7</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Ashley</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">7</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> ]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">todo</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Be funny</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Manage household</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">email</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">bill@example.com</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">version</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> inc </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">i</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #C792EA">=></span><span style="color: #A6ACCD"> i </span><span style="color: #89DDFF">+</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> eq </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">x</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #C792EA">=></span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">y</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #C792EA">=></span><span style="color: #A6ACCD"> x </span><span style="color: #89DDFF">===</span><span style="color: #A6ACCD"> y</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> newPerson </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(person</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #89DDFF"> </span><span style="color: #676E95">// Change first name</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">first</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Bob</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #89DDFF"> </span><span style="color: #676E95">// Increment all children's ages</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">children</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">map</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> inc </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF"> </span><span style="color: #676E95">// Update email</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">email</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">bob@example.com</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF"> </span><span style="color: #676E95">// Remove todo</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">todo</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">reject</span><span style="color: #A6ACCD">(</span><span style="color: #82AAFF">eq</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Be funny</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD">))</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF"> </span><span style="color: #676E95">// Increment version</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">version</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> inc</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #676E95">// => {</span></span>
|
||||
<span class="line"><span style="color: #676E95">// name: { first: 'Bob', last: 'Sagat' },</span></span>
|
||||
<span class="line"><span style="color: #676E95">// children: [</span></span>
|
||||
<span class="line"><span style="color: #676E95">// { name: 'Mary-Kate', age: 8 },</span></span>
|
||||
<span class="line"><span style="color: #676E95">// { name: 'Ashley', age: 8 }</span></span>
|
||||
<span class="line"><span style="color: #676E95">// ],</span></span>
|
||||
<span class="line"><span style="color: #676E95">// todo: [</span></span>
|
||||
<span class="line"><span style="color: #676E95">// 'Manage household'</span></span>
|
||||
<span class="line"><span style="color: #676E95">// ],</span></span>
|
||||
<span class="line"><span style="color: #676E95">// email: 'bob@example.com',</span></span>
|
||||
<span class="line"><span style="color: #676E95">// version: 2</span></span>
|
||||
<span class="line"><span style="color: #676E95">//}</span></span>
|
||||
<span class="line"></span></code></pre>`}}),{c(){e=t("h1"),p=y("updeep-remeda"),i=F(),g=t("blockquote"),_=t("p"),h=y(`Easily update nested frozen objects and arrays in a declarative and immutable
|
||||
manner.`),E=F(),w=t("h2"),A(j.$$.fragment),ks=y(" About"),Cs=F(),A(P.$$.fragment),As=F(),J=t("p"),ws=y(`updeep makes updating deeply nested objects/arrays painless by allowing you to
|
||||
declare the updates you would like to make and it will take care of the rest. It
|
||||
will recursively return the same instance if no changes have been made, making
|
||||
it ideal for using reference equality checks to detect changes.`),fs=F(),V=t("p"),qs=y(`Because of this, everything returned by updeep is frozen. Not only that, but
|
||||
updeep assumes that every object passed in to update is immutable, so it may
|
||||
freeze objects passed in as well. Note that the freezing only happens in
|
||||
development.`),us=F(),X=t("p"),xs=y("This fork of updeep requires Remeda, but works very well with any other utility function ([lodash], [Ramda], etc)."),ms=F(),q=t("h2"),A(z.$$.fragment),Is=y(" Differences with the original Updeep"),ds=F(),v=t("ul"),ns=t("li"),as=t("p"),js=y(`Under the hood, the use of lodash has
|
||||
been replaced by Remeda (for better type support and tree-shaking abilities).`),Ps=F(),es=t("li"),ls=t("p"),zs=y("The codebase has been ported to TypeScript (mostly for the lulz)."),Ts=F(),ps=t("li"),os=t("p"),Ls=y("The order of parameters in the non-curryied invocation of functions has been modified. In the original updeep the input object is the last parameter, whereas here it's the first."),$s=F(),A(O.$$.fragment),T=t("ul"),ts=t("li"),k=t("p"),A(S.$$.fragment),Rs=y(` has been removed as the behavior can be implemented using
|
||||
Remeda's `),A(H.$$.fragment),Bs=y(", or a simple "),A(M.$$.fragment),Us=y("."),Os=F(),rs=t("li"),L=t("p"),A(N.$$.fragment),Ss=y(" has been renamed "),A(K.$$.fragment),Hs=y("."),hs=F(),x=t("h2"),A(R.$$.fragment),Ms=y(" Installation"),bs=F(),A(Q.$$.fragment),I=t("h2"),A(B.$$.fragment),Ns=y(" Full example"),Es=F(),A(W.$$.fragment),this.h()},l(s){e=r(s,"H1",{});var a=c(e);p=D(a,"updeep-remeda"),a.forEach(n),i=C(s),g=r(s,"BLOCKQUOTE",{});var cs=c(g);_=r(cs,"P",{});var ys=c(_);h=D(ys,`Easily update nested frozen objects and arrays in a declarative and immutable
|
||||
manner.`),ys.forEach(n),cs.forEach(n),E=C(s),w=r(s,"H2",{id:!0,tabindex:!0});var Y=c(w);f(j.$$.fragment,Y),ks=D(Y," About"),Y.forEach(n),Cs=C(s),f(P.$$.fragment,s),As=C(s),J=r(s,"P",{});var Ds=c(J);ws=D(Ds,`updeep makes updating deeply nested objects/arrays painless by allowing you to
|
||||
declare the updates you would like to make and it will take care of the rest. It
|
||||
will recursively return the same instance if no changes have been made, making
|
||||
it ideal for using reference equality checks to detect changes.`),Ds.forEach(n),fs=C(s),V=r(s,"P",{});var is=c(V);qs=D(is,`Because of this, everything returned by updeep is frozen. Not only that, but
|
||||
updeep assumes that every object passed in to update is immutable, so it may
|
||||
freeze objects passed in as well. Note that the freezing only happens in
|
||||
development.`),is.forEach(n),us=C(s),X=r(s,"P",{});var Js=c(X);xs=D(Js,"This fork of updeep requires Remeda, but works very well with any other utility function ([lodash], [Ramda], etc)."),Js.forEach(n),ms=C(s),q=r(s,"H2",{id:!0,tabindex:!0});var Ks=c(q);f(z.$$.fragment,Ks),Is=D(Ks," Differences with the original Updeep"),Ks.forEach(n),ds=C(s),v=r(s,"UL",{});var Z=c(v);ns=r(Z,"LI",{});var Vs=c(ns);as=r(Vs,"P",{});var Xs=c(as);js=D(Xs,`Under the hood, the use of lodash has
|
||||
been replaced by Remeda (for better type support and tree-shaking abilities).`),Xs.forEach(n),Vs.forEach(n),Ps=C(Z),es=r(Z,"LI",{});var Ys=c(es);ls=r(Ys,"P",{});var Zs=c(ls);zs=D(Zs,"The codebase has been ported to TypeScript (mostly for the lulz)."),Zs.forEach(n),Ys.forEach(n),Ts=C(Z),ps=r(Z,"LI",{});var sn=c(ps);os=r(sn,"P",{});var nn=c(os);Ls=D(nn,"The order of parameters in the non-curryied invocation of functions has been modified. In the original updeep the input object is the last parameter, whereas here it's the first."),nn.forEach(n),sn.forEach(n),Z.forEach(n),$s=C(s),f(O.$$.fragment,s),T=r(s,"UL",{});var _s=c(T);ts=r(_s,"LI",{});var an=c(ts);k=r(an,"P",{});var G=c(k);f(S.$$.fragment,G),Rs=D(G,` has been removed as the behavior can be implemented using
|
||||
Remeda's `),f(H.$$.fragment,G),Bs=D(G,", or a simple "),f(M.$$.fragment,G),Us=D(G,"."),G.forEach(n),an.forEach(n),Os=C(_s),rs=r(_s,"LI",{});var en=c(rs);L=r(en,"P",{});var Fs=c(L);f(N.$$.fragment,Fs),Ss=D(Fs," has been renamed "),f(K.$$.fragment,Fs),Hs=D(Fs,"."),Fs.forEach(n),en.forEach(n),_s.forEach(n),hs=C(s),x=r(s,"H2",{id:!0,tabindex:!0});var Qs=c(x);f(R.$$.fragment,Qs),Ms=D(Qs," Installation"),Qs.forEach(n),bs=C(s),f(Q.$$.fragment,s),I=r(s,"H2",{id:!0,tabindex:!0});var Ws=c(I);f(B.$$.fragment,Ws),Ns=D(Ws," Full example"),Ws.forEach(n),Es=C(s),f(W.$$.fragment,s),this.h()},h(){U(w,"id","about"),U(w,"tabindex","-1"),U(q,"id","differences-with-the-original-updeep"),U(q,"tabindex","-1"),U(x,"id","installation"),U(x,"tabindex","-1"),U(I,"id","full-example"),U(I,"tabindex","-1")},m(s,a){o(s,e,a),l(e,p),o(s,i,a),o(s,g,a),l(g,_),l(_,h),o(s,E,a),o(s,w,a),u(j,w,null),l(w,ks),o(s,Cs,a),u(P,s,a),o(s,As,a),o(s,J,a),l(J,ws),o(s,fs,a),o(s,V,a),l(V,qs),o(s,us,a),o(s,X,a),l(X,xs),o(s,ms,a),o(s,q,a),u(z,q,null),l(q,Is),o(s,ds,a),o(s,v,a),l(v,ns),l(ns,as),l(as,js),l(v,Ps),l(v,es),l(es,ls),l(ls,zs),l(v,Ts),l(v,ps),l(ps,os),l(os,Ls),o(s,$s,a),u(O,s,a),o(s,T,a),l(T,ts),l(ts,k),u(S,k,null),l(k,Rs),u(H,k,null),l(k,Bs),u(M,k,null),l(k,Us),l(T,Os),l(T,rs),l(rs,L),u(N,L,null),l(L,Ss),u(K,L,null),l(L,Hs),o(s,hs,a),o(s,x,a),u(R,x,null),l(x,Ms),o(s,bs,a),u(Q,s,a),o(s,I,a),u(B,I,null),l(I,Ns),o(s,Es,a),u(W,s,a),gs=!0},p(s,[a]){const cs={};a&1&&(cs.$$scope={dirty:a,ctx:s}),j.$set(cs);const ys={};a&1&&(ys.$$scope={dirty:a,ctx:s}),P.$set(ys);const Y={};a&1&&(Y.$$scope={dirty:a,ctx:s}),z.$set(Y);const Ds={};a&1&&(Ds.$$scope={dirty:a,ctx:s}),R.$set(Ds);const is={};a&1&&(is.$$scope={dirty:a,ctx:s}),B.$set(is)},i(s){gs||(m(j.$$.fragment,s),m(P.$$.fragment,s),m(z.$$.fragment,s),m(O.$$.fragment,s),m(S.$$.fragment,s),m(H.$$.fragment,s),m(M.$$.fragment,s),m(N.$$.fragment,s),m(K.$$.fragment,s),m(R.$$.fragment,s),m(Q.$$.fragment,s),m(B.$$.fragment,s),m(W.$$.fragment,s),gs=!0)},o(s){d(j.$$.fragment,s),d(P.$$.fragment,s),d(z.$$.fragment,s),d(O.$$.fragment,s),d(S.$$.fragment,s),d(H.$$.fragment,s),d(M.$$.fragment,s),d(N.$$.fragment,s),d(K.$$.fragment,s),d(R.$$.fragment,s),d(Q.$$.fragment,s),d(B.$$.fragment,s),d(W.$$.fragment,s),gs=!1},d(s){s&&n(e),s&&n(i),s&&n(g),s&&n(E),s&&n(w),$(j),s&&n(Cs),$(P,s),s&&n(As),s&&n(J),s&&n(fs),s&&n(V),s&&n(us),s&&n(X),s&&n(ms),s&&n(q),$(z),s&&n(ds),s&&n(v),s&&n($s),$(O,s),s&&n(T),$(S),$(H),$(M),$(N),$(K),s&&n(hs),s&&n(x),$(R),s&&n(bs),$(Q,s),s&&n(I),$(B),s&&n(Es),$(W,s)}}}class mn extends ln{constructor(e){super(),pn(this,e,null,An,on,{})}}export{mn as default};
|
@ -1 +0,0 @@
|
||||
import{l as a,p as o}from"../../chunks/_layout-32f74dae.js";export{a as load,o as prerender};
|
@ -1 +0,0 @@
|
||||
import"../../chunks/index-35a671a5.js";import{l as p,p as a}from"../../chunks/_page-a27df1e4.js";export{p as load,a as prerender};
|
@ -1 +0,0 @@
|
||||
import"../../../chunks/index-35a671a5.js";import{l as p,p as a}from"../../../chunks/_page-115bdbbb.js";export{p as load,a as prerender};
|
File diff suppressed because one or more lines are too long
@ -1 +0,0 @@
|
||||
{"version":"1673374967075"}
|
2
docs/_navbar.md
Normal file
2
docs/_navbar.md
Normal file
@ -0,0 +1,2 @@
|
||||
- [Getting started](/)
|
||||
- [API](/api)
|
95
docs/docsify-namespaced.js
Normal file
95
docs/docsify-namespaced.js
Normal file
@ -0,0 +1,95 @@
|
||||
/*!
|
||||
* docsify-namespaced
|
||||
* v0.1.1
|
||||
* https://github.com/palkan/docsify-namespaced
|
||||
* (c) 2020-2021 Vladimir Dementyev <dementiev.vm@gmail.com>
|
||||
* MIT license
|
||||
*/
|
||||
!(function () {
|
||||
"use strict";
|
||||
(window.$docsify = window.$docsify || {}),
|
||||
(window.$docsify.plugins = [
|
||||
function (n, a) {
|
||||
function r(n) {
|
||||
w ? (window.location.hash = n) : (window.location.href = n);
|
||||
}
|
||||
function l(n) {
|
||||
return (n =
|
||||
n || (w ? window.location.hash : window.location.pathname)).split(
|
||||
/\//
|
||||
);
|
||||
}
|
||||
function u(n, e, o, t) {
|
||||
e.values.includes(n[o + 1])
|
||||
? t
|
||||
? (n[o + 1] = t)
|
||||
: n.splice(o + 1, 1)
|
||||
: t && n.splice(o + 1, 0, t);
|
||||
}
|
||||
var s,
|
||||
f,
|
||||
d,
|
||||
w = !0;
|
||||
n.mounted(function () {
|
||||
var n = (s = a.config.namespaces).map(function (n) {
|
||||
var e = "(?:(".concat(n.values.join("|"), ")/)");
|
||||
return n.optional && (e += "?"), e;
|
||||
});
|
||||
(f = new RegExp("^#?/".concat(n.join("")))),
|
||||
(w = "hash" === a.router.mode);
|
||||
var o = l(),
|
||||
e = o.join("/"),
|
||||
t = 2 === o.length && "" === o[1];
|
||||
s.forEach(function (n, e) {
|
||||
n.selector &&
|
||||
((n.selectElement = Docsify.dom.find(n.selector)),
|
||||
n.default &&
|
||||
((n.selectElement.value = n.default),
|
||||
n.values.includes(o[e + 1]) || u(o, n, e, n.default)),
|
||||
Docsify.dom.on(n.selectElement, "click", function (n) {
|
||||
return n.stopPropagation();
|
||||
}),
|
||||
Docsify.dom.on(n.selectElement, "change", function (n) {
|
||||
return (function (n, e) {
|
||||
var o = l();
|
||||
u(o, s[e], e, n);
|
||||
var t = o.join("/");
|
||||
r(t);
|
||||
})(n.target.value, e);
|
||||
}));
|
||||
});
|
||||
var c = a.compiler.sidebar;
|
||||
a.compiler.sidebar = function () {
|
||||
return (function (n) {
|
||||
if (!d) return n;
|
||||
var c = new RegExp("^" + d);
|
||||
return (n = n.replace(
|
||||
/(href=['"])(#?[^'"]+)(["'])/g,
|
||||
function (n, e, o, t) {
|
||||
console.log('!!!',o);
|
||||
return o.match(c)
|
||||
? n
|
||||
: [e, (o = o.replace(/^#?\//, d)), t].join("");
|
||||
}
|
||||
));
|
||||
})(c.apply(this, arguments));
|
||||
};
|
||||
var i = o.join("/");
|
||||
t && i !== e && r(i);
|
||||
}),
|
||||
n.afterEach(function (n, e) {
|
||||
var o = (w ? window.location.hash : window.location.pathname).match(
|
||||
f
|
||||
);
|
||||
s.forEach(function (n, e) {
|
||||
n.selectElement &&
|
||||
(n.selectElement.value = (o && o[e + 1]) || "");
|
||||
}),
|
||||
(d = o ? o[0] : "/"),
|
||||
(a.config.currentNamespace = d),
|
||||
e(n);
|
||||
});
|
||||
},
|
||||
].concat(window.$docsify.plugins || []));
|
||||
})();
|
||||
//# sourceMappingURL=docsify-namespaced.min.js.map
|
BIN
docs/favicon.png
BIN
docs/favicon.png
Binary file not shown.
Before Width: | Height: | Size: 1.5 KiB |
@ -1 +1,60 @@
|
||||
<meta http-equiv="refresh" content="0;url=/latest/get-started">
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<title>Document</title>
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
|
||||
<meta name="description" content="Description" />
|
||||
<meta
|
||||
name="viewport"
|
||||
content="width=device-width, initial-scale=1.0, minimum-scale=1.0"
|
||||
/>
|
||||
<link rel="stylesheet" href="vendor/themes/vue.css" />
|
||||
<style>
|
||||
div.info {
|
||||
background: lightgreen;
|
||||
margin: 0px 2em;
|
||||
padding: 0.25em 1em;
|
||||
font-weight: normal;
|
||||
border-radius: 1em;
|
||||
color: black;
|
||||
}
|
||||
|
||||
|
||||
div.info h4 {
|
||||
margin: 0px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<div id="app"></div>
|
||||
<script>
|
||||
window.$docsify = {
|
||||
loadNavbar: true,
|
||||
name: "updeep-remeda",
|
||||
repo: "https://github.com/yanick/updeep-remeda",
|
||||
alias: {
|
||||
"/api": "/latest/api",
|
||||
},
|
||||
namespaces: [
|
||||
{
|
||||
id: "version",
|
||||
values: ["latest"],
|
||||
optional: true,
|
||||
default: "latest",
|
||||
selector: "#version-selector",
|
||||
},
|
||||
],
|
||||
name:
|
||||
'<a id="home-link" class="app-name-link" data-nosearch href="/">updeep-remeda</a> ' +
|
||||
'<select id="version-selector" name="version">' +
|
||||
'<option value="latest">latest</value>' +
|
||||
"</select>",
|
||||
// disable automatic linking to avoid navigating when clicking on select
|
||||
nameLink: false,
|
||||
};
|
||||
</script>
|
||||
<script src="docsify-namespaced.js"></script>
|
||||
<script src="vendor/docsify.js"></script>
|
||||
</body>
|
||||
</html>
|
||||
|
@ -1 +0,0 @@
|
||||
{"excerpt":"","headers":[{"level":2,"title":"Importing","slug":"importing","children":[]},{"level":2,"title":"u(dataIn, updates)","slug":"u-datain-updates","children":[]},{"level":2,"title":"u.update(dataIn, updates)","slug":"u-update-datain-updates","children":[{"level":3,"title":"Simple update","slug":"simple-update","children":[]},{"level":3,"title":"Multiple updates","slug":"multiple-updates","children":[]},{"level":3,"title":"Use a function","slug":"use-a-function","children":[]},{"level":3,"title":"Array Manipulation","slug":"array-manipulation","children":[]},{"level":3,"title":"Default input data","slug":"default-input-data","children":[]},{"level":3,"title":"Partial application","slug":"partial-application","children":[]}]},{"level":2,"title":"u.freeze(dataIn)","slug":"u-freeze-datain","children":[]},{"level":2,"title":"u.updateIn(dataIn, path, value)","slug":"u-updatein-datain-path-value","children":[]},{"level":2,"title":"u.constant(dataIn)","slug":"u-constant-datain","children":[]},{"level":2,"title":"u.if(dataIn, predicate, updates)","slug":"u-if-datain-predicate-updates","children":[]},{"level":2,"title":"u.filter(arrayIn, predicate)","slug":"u-filter-arrayin-predicate","children":[]},{"level":2,"title":"u.reject(arrayIn, predicate)","slug":"u-reject-arrayin-predicate","children":[]},{"level":2,"title":"u.pickBy(objectIn, predicate)","slug":"u-pickby-objectin-predicate","children":[]},{"level":2,"title":"u.omitBy(objectIn, predicate)","slug":"u-omitby-objectin-predicate","children":[]},{"level":2,"title":"u.pick(objectIn, keys)","slug":"u-pick-objectin-keys","children":[]},{"level":2,"title":"u.omit(objectIn, keys)","slug":"u-omit-objectin-keys","children":[]},{"level":2,"title":"u.matches(dataIn, condition)","slug":"u-matches-datain-condition","children":[]}],"title":"API","frontmatter":{"title":"API"},"lastUpdated":1673371541420}
|
@ -1 +0,0 @@
|
||||
{"excerpt":"","headers":[{"level":2,"title":"About","slug":"about","children":[]},{"level":2,"title":"Differences with the original Updeep","slug":"differences-with-the-original-updeep","children":[]},{"level":2,"title":"Installation","slug":"installation","children":[]},{"level":2,"title":"Full example","slug":"full-example","children":[]}],"title":"Get Started","frontmatter":{"title":"Get Started"},"lastUpdated":1673371541420}
|
@ -1 +0,0 @@
|
||||
<meta http-equiv="refresh" content="0;url=/latest/get-started">
|
@ -1,7 +1,3 @@
|
||||
---
|
||||
title: Get Started
|
||||
---
|
||||
|
||||
# updeep-remeda
|
||||
|
||||
> Easily update nested frozen objects and arrays in a declarative and immutable
|
||||
@ -9,14 +5,15 @@ title: Get Started
|
||||
|
||||
## About
|
||||
|
||||
:::info
|
||||
<div class="info">
|
||||
<h4>💡 Info</h4>
|
||||
|
||||
This is a fork of the main updeep package. For ease of reading — not to
|
||||
mention ease of shamelessly lifting large pieces of the original
|
||||
documentation — in this documentation all mentions of `updeep` refers to this
|
||||
fork.
|
||||
|
||||
:::
|
||||
</div>
|
||||
|
||||
updeep makes updating deeply nested objects/arrays painless by allowing you to
|
||||
declare the updates you would like to make and it will take care of the rest. It
|
||||
@ -32,12 +29,12 @@ This fork of updeep requires Remeda, but works very well with any other utility
|
||||
|
||||
## Differences with the original Updeep
|
||||
|
||||
* Under the hood, the use of lodash has
|
||||
- Under the hood, the use of lodash has
|
||||
been replaced by Remeda (for better type support and tree-shaking abilities).
|
||||
|
||||
* The codebase has been ported to TypeScript (mostly for the lulz).
|
||||
- The codebase has been ported to TypeScript (mostly for the lulz).
|
||||
|
||||
* The order of parameters in the non-curryied invocation of functions has been modified. In the original updeep the input object is the last parameter, whereas here it's the first.
|
||||
- The order of parameters in the non-curryied invocation of functions has been modified. In the original updeep the input object is the last parameter, whereas here it's the first.
|
||||
|
||||
```js
|
||||
// original updeep
|
||||
@ -51,10 +48,10 @@ dataOut = u(dataIn, { c: 3 }); // simple call
|
||||
dataOut = u({ c: 3 })(dataIn); // curried
|
||||
```
|
||||
|
||||
* `withDefault` has been removed as the behavior can be implemented using
|
||||
- `withDefault` has been removed as the behavior can be implemented using
|
||||
Remeda's `pipe`, or a simple `??`.
|
||||
|
||||
* `u.omitted` has been renamed `u.skip`.
|
||||
- `u.omitted` has been renamed `u.skip`.
|
||||
|
||||
## Installation
|
||||
|
2
docs/latest/_navbar.md
Normal file
2
docs/latest/_navbar.md
Normal file
@ -0,0 +1,2 @@
|
||||
- [Getting started](/latest/)
|
||||
- [API](/latest/api)
|
@ -1,525 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<link rel="icon" href="../favicon.png" />
|
||||
<meta name="viewport" content="width=device-width" />
|
||||
|
||||
<script>
|
||||
const key = 'svelteness::color-scheme';
|
||||
const scheme = localStorage[key];
|
||||
const prefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches;
|
||||
if (scheme === 'dark' || (scheme !== 'light' && prefersDark)) {
|
||||
document.documentElement.classList.add('dark');
|
||||
} else {
|
||||
document.documentElement.classList.remove('dark');
|
||||
}
|
||||
</script>
|
||||
|
||||
<meta http-equiv="content-security-policy" content="">
|
||||
<link href="../_app/immutable/assets/_layout-d4f4ab95.css" rel="stylesheet">
|
||||
<link href="../_app/immutable/assets/Info-eb9b7651.css" rel="stylesheet">
|
||||
<link rel="modulepreload" href="../_app/immutable/start-4894d21d.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/singletons-79165f10.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/control-f5b05b5f.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/components/pages/_layout.svelte-ac40f340.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/contexts-c54c563b.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/stores-1c9d0b64.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/modules/pages/_layout.js-82ef414d.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/_layout-32f74dae.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/components/pages/latest/api/_page.md-bd91dac8.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/Info-8cb253a1.js">
|
||||
</head>
|
||||
<body data-sveltekit-preload-data="hover">
|
||||
<div style="display: contents">
|
||||
|
||||
|
||||
<div class="kit-docs bg-gray-body min-h-full min-w-full h-full transition-transform duration-150 ease-out" style="font-family: var(--kd-font-family-sans, inherit); --kd--navbar-height: calc(var(--kd-navbar-height) + var(--kd-breadcrumbs-height));"><div class="fixed top-0 z-30 w-full flex-none transform-gpu transition-transform duration-150 ease-out supports-backdrop-blur:bg-white/60 bg-gray-200/95 backdrop-blur dark:bg-gray-800/60 translate-y-0" style="border-bottom: var(--kd-navbar-border-bottom);"><div class="flex w-full flex-col items-center justify-center mx-auto max-w-[var(--kd-navbar-max-width)] p-[var(--kd-navbar-padding)] h-[var(--kd--navbar-height)]"><div class="flex w-full items-center">
|
||||
|
||||
|
||||
<div class="flex-1"></div>
|
||||
|
||||
<div class="992:hidden -mr-2 flex items-center">
|
||||
|
||||
<div class="relative inline-block text-left not-prose"><button id="popover-button-1" type="button" class="inline-flex w-full justify-center rounded-md p-2 text-lg font-medium text-gray-soft hover:text-gray-inverse" aria-controls="popover-1" aria-expanded="false" aria-haspopup="true"><svg viewBox="0 0 24 24" width="30" height="30"><!-- HTML_TAG_START --><path fill="currentColor" d="M18 18v2H6v-2h12zm3-7v2H3v-2h18zm-3-7v2H6V4h12z"/><!-- HTML_TAG_END --></svg>
|
||||
<span class="sr-only">Main navigation menu</span>
|
||||
</button>
|
||||
|
||||
<div class="fixed top-0 left-0 bg-black/40 backdrop-blur-sm dark:bg-gray-700/80 transition-opacity duration-75 pointer-events-auto z-40 w-screen h-screen opacity-0 invisible"></div>
|
||||
|
||||
<div hidden></div>
|
||||
|
||||
</div></div>
|
||||
|
||||
<div class="992:flex 992:items-center hidden"><nav><ul class="flex items-center space-x-8 text-lg font-medium"><li class="mt-4 first:mt-0 992:mt-0"><a class="p-1 text-gray-soft hover:text-gray-inverse" href="/latest/get-started">Get started</a></li><li class="mt-4 first:mt-0 992:mt-0"><a class="p-1 border-b hover:border-b-2 border-brand text-gray-inverse" href="/latest/api">API</a></li></ul></nav>
|
||||
|
||||
|
||||
|
||||
|
||||
<div class="border-gray-divider ml-6 mr-2.5 h-7 w-2 border-l-[1.5px]"></div>
|
||||
|
||||
<div class="hidden 992:flex items-center">
|
||||
|
||||
<div class="relative inline-block text-left not-prose"><button id="menu-button-1" type="button" class="inline-flex w-full justify-center rounded-md p-2 text-lg font-medium text-gray-soft hover:text-gray-inverse" aria-controls="menu-1" aria-expanded="false" aria-haspopup="true"><svg viewBox="0 0 24 24" width="1.2em" height="1.2em" class="h-6 w-6"><!-- HTML_TAG_START --><path fill="currentColor" d="M12 18a6 6 0 1 1 0-12a6 6 0 0 1 0 12zM11 1h2v3h-2V1zm0 19h2v3h-2v-3zM3.515 4.929l1.414-1.414L7.05 5.636L5.636 7.05L3.515 4.93zM16.95 18.364l1.414-1.414l2.121 2.121l-1.414 1.414l-2.121-2.121zm2.121-14.85l1.414 1.415l-2.121 2.121l-1.414-1.414l2.121-2.121zM5.636 16.95l1.414 1.414l-2.121 2.121l-1.414-1.414l2.121-2.121zM23 11v2h-3v-2h3zM4 11v2H1v-2h3z"/><!-- HTML_TAG_END --></svg>
|
||||
<span class="sr-only">Color Scheme</span>
|
||||
</button>
|
||||
|
||||
<div hidden></div>
|
||||
|
||||
</div></div></div></div>
|
||||
|
||||
<div class="border-gray-divider 992:hidden flex w-full items-center mt-4 pt-4 border-t"><button id="main-sidebar-button" type="button" class="text-gray-soft hover:text-gray-inverse inline-flex justify-center rounded-md p-2 text-sm font-medium" aria-controls="main-sidebar" aria-expanded="false" aria-haspopup="true"><span class="sr-only">Open main sidebar</span>
|
||||
<svg viewBox="0 0 24 24" width="28" height="28"><!-- HTML_TAG_START --><path fill="currentColor" d="M21 18v2H3v-2h18zM17.05 3.55L22 8.5l-4.95 4.95v-9.9zM12 11v2H3v-2h9zm0-7v2H3V4h9z"/><!-- HTML_TAG_END --></svg></button>
|
||||
|
||||
<ol class="text-md text-gray-soft flex items-center whitespace-nowrap leading-6 mt-px ml-2.5">
|
||||
<li class="truncate font-semibold text-slate-900 dark:text-slate-200">API</li></ol></div>
|
||||
|
||||
|
||||
</div></div>
|
||||
|
||||
<div class="mx-auto w-full flex flex-row min-h-full max-w-[var(--kd-content-max-width)] pt-[var(--kd--navbar-height)] z-20"><aside id="main-sidebar" class="sidebar self-start fixed top-0 left-0 transform bg-gray-body z-50 border-gray-divider border-r -translate-x-full transform transition-transform duration-200 ease-out will-change-transform max-h-screen min-h-screen min-w-[var(--kd-sidebar-min-width)] max-w-[var(--kd-sidebar-max-width)] 992:translate-x-0 922:block 992:sticky 992:z-0 overflow-y-auto p-[var(--kd-sidebar-padding)] 992:top-[var(--kd--navbar-height)] 992:min-h-[calc(100vh-var(--kd--navbar-height))] 992:max-h-[calc(100vh-var(--kd--navbar-height))]" role="dialog" aria-modal="true" style=""><div class="992:hidden sticky top-0 left-0 flex items-center"><div class="flex-1"></div>
|
||||
<button class="text-gray-soft hover:text-gray-inverse p-4 -mx-6 pointer-events-none"><svg viewBox="0 0 24 24" width="24" height="24"><!-- HTML_TAG_START --><path fill="currentColor" d="m12 10.586l4.95-4.95l1.414 1.414l-4.95 4.95l4.95 4.95l-1.414 1.414l-4.95-4.95l-4.95 4.95l-1.414-1.414l4.95-4.95l-4.95-4.95L7.05 5.636z"/><!-- HTML_TAG_END --></svg>
|
||||
<span class="sr-only">Close sidebar</span></button></div>
|
||||
|
||||
<nav class="992:px-1">
|
||||
|
||||
|
||||
|
||||
<ul class="mt-8 pb-28 992:pb-0">
|
||||
<li class="992:mt-10 mt-12 first:mt-0"><h5 class="text-gray-strong 992:mb-3 mb-8 text-lg font-semibold">
|
||||
</h5>
|
||||
<ul class="border-gray-divider space-y-3 border-l"><li class="first:mt-6"><a class="992:py-1.5 -ml-px flex items-center border-l-2 py-2 pl-4 hover:border-gray-inverse text-gray-soft hover:text-gray-inverse border-transparent font-normal" href="/latest/get-started" style="">
|
||||
Get started
|
||||
</a>
|
||||
</li><li class="first:mt-6"><a class="992:py-1.5 -ml-px flex items-center border-l-2 py-2 pl-4 text-brand font-semibold" href="/latest/api" style="border-color: var(--kd-sidebar-border-active);">
|
||||
API
|
||||
</a>
|
||||
</li></ul>
|
||||
</li></ul>
|
||||
|
||||
|
||||
</nav></aside>
|
||||
|
||||
<div class="992:hidden z-40"><div class="fixed top-0 left-0 bg-black/40 backdrop-blur-sm dark:bg-gray-700/80 transition-opacity duration-75 pointer-events-auto z-40 w-screen h-screen opacity-0 invisible"></div></div>
|
||||
|
||||
<main class="w-full overflow-x-hidden 992:min-h-[calc(100vh-var(--kd--navbar-height))] min-h-[calc(100vh-var(--kd--navbar-height))] px-8 992:px-16 pt-8" style="max-width: var(--kd-main-max-width, var(--kd-article-max-width));">
|
||||
|
||||
<article class="markdown prose dark:prose-invert z-10 max-w-[var(--kd-article-max-width)]">
|
||||
|
||||
<h1>API</h1>
|
||||
<div class="svelte-ns3bhs"><h4 class="svelte-ns3bhs">💡 Info</h4>
|
||||
|
||||
<p>All functions are curried, Remeda-style, so if you see <code>f(dataIn, ...others)</code>, it can be called with either <code>f(dataIn, ...others)</code> or <code>f(...others)(dataIn)</code>.</p>
|
||||
|
||||
</div>
|
||||
<h2 id="importing" tabindex="-1">
|
||||
<a class="header-anchor" href="#importing" aria-hidden="true">#</a> Importing</h2>
|
||||
<p><code>updeep-remeda</code> exports a default function that is an alias to <code>u.update</code> and
|
||||
has all the other functions available as props.</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-text ext-text" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: undefined">import u from '@yanick/updeep-remeda';</span></span>
|
||||
<span class="line"><span style="color: undefined"></span></span>
|
||||
<span class="line"><span style="color: undefined">const foo = u({a:1}, { a: x => x + 1 });</span></span>
|
||||
<span class="line"><span style="color: undefined"></span></span>
|
||||
<span class="line"><span style="color: undefined">const bar = u.updateIn({ a: { b: 2 } }, 'a.b', 3 );</span></span>
|
||||
<span class="line"><span style="color: undefined"></span></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><p>Or you can import the functions piecemeal:</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-text ext-text" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: undefined">import { updateIn, omit } from '@yanick/updeep-remeda';</span></span>
|
||||
<span class="line"><span style="color: undefined"></span></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h2 id="u-datain-updates" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-datain-updates" aria-hidden="true">#</a> <code>u(dataIn, updates)</code></h2>
|
||||
<h2 id="u-update-datain-updates" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-update-datain-updates" aria-hidden="true">#</a> <code>u.update(dataIn, updates)</code></h2>
|
||||
<p>Update as many values as you want, as deeply as you want. The <code>updates</code> parameter can either be an object, a function, or a value. Everything returned from <code>u</code> is frozen recursively.</p>
|
||||
<p>If <code>updates</code> is an object, for each key/value, it will apply the updates specified in the value to <code>object[key]</code>.</p>
|
||||
<p>If <code>updates</code> is a function, it will call the function with <code>object</code> and return the value.</p>
|
||||
<p>If <code>updates</code> is a value, it will return that value.</p>
|
||||
<p>Sometimes, you may want to set an entire object to a property, or a function. In that case, you'll need to use a function to return that value, otherwise it would be interpreted as an update. Ex. <code>function() { return { a: 0 }; }</code>.</p>
|
||||
<p>Also available at <code>u.update(...)</code>.</p>
|
||||
<h3 id="simple-update" tabindex="-1">
|
||||
<a class="header-anchor" href="#simple-update" aria-hidden="true">#</a> Simple update</h3>
|
||||
<p>Object properties:</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> person </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">first</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Jane</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">last</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">West</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(person</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">first</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Susan</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">first</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Susan</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">last</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">West</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><p>Array elements:</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> scoreboard </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">scores</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #F78C6C">12</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">28</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(scoreboard</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">scores</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">36</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">scores</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #F78C6C">12</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">36</span><span style="color: #A6ACCD">] </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h3 id="multiple-updates" tabindex="-1">
|
||||
<a class="header-anchor" href="#multiple-updates" aria-hidden="true">#</a> Multiple updates</h3>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> person </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">first</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Mike</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">last</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Smith</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">scores</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #F78C6C">12</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">28</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(person</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">last</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Jones</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">scores</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">36</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">first</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Mike</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">last</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Jones</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">scores</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #F78C6C">12</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">36</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h3 id="use-a-function" tabindex="-1">
|
||||
<a class="header-anchor" href="#use-a-function" aria-hidden="true">#</a> Use a function</h3>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> increment </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">i</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #C792EA">=></span><span style="color: #A6ACCD"> i </span><span style="color: #89DDFF">+</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">var</span><span style="color: #A6ACCD"> scoreboard </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">scores</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">team1</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">0</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">team2</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">0</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(scoreboard</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">scores</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">team2</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> increment </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">scores</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">team1</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">0</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">team2</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h3 id="array-manipulation" tabindex="-1">
|
||||
<a class="header-anchor" href="#array-manipulation" aria-hidden="true">#</a> Array Manipulation</h3>
|
||||
<p>Non-trivial array manipulations, such as element removal/insertion/sorting, can be implemented with functions. Because there are so many possible manipulations, we don't provide any helpers and leave this up to you. Simply ensure your function is pure and does not mutate its arguments.</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">function</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">addTodo</span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">todos</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #F07178"> </span><span style="color: #89DDFF">return</span><span style="color: #F07178"> []</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">concat</span><span style="color: #F07178">(</span><span style="color: #A6ACCD">todos</span><span style="color: #89DDFF">,</span><span style="color: #F07178"> [</span><span style="color: #89DDFF">{</span><span style="color: #F07178"> done</span><span style="color: #89DDFF">:</span><span style="color: #F07178"> </span><span style="color: #FF9CAC">false</span><span style="color: #F07178"> </span><span style="color: #89DDFF">}</span><span style="color: #F07178">])</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">}</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> state </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">todos</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">todos</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> addTodo </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> state)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">todos</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><p>Remeda is one of the many libraries providing good utility functions for
|
||||
such manipulations.</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #89DDFF">import</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #F07178"> </span><span style="color: #A6ACCD">reject</span><span style="color: #89DDFF">,</span><span style="color: #F07178"> </span><span style="color: #A6ACCD">concat</span><span style="color: #89DDFF">,</span><span style="color: #F07178"> </span><span style="color: #A6ACCD">prop</span><span style="color: #F07178"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">from</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">remeda</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">let</span><span style="color: #A6ACCD"> state </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">todos</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">true</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #676E95">// add a new todo</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">state </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(state</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">todos</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">concat</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">) </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(state)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">todos</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">true</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #676E95">// remove all done todos</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">state </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(state</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">todos</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">reject</span><span style="color: #A6ACCD">(</span><span style="color: #82AAFF">prop</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">done</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD">)) </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(state)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">todos</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">] </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h3 id="default-input-data" tabindex="-1">
|
||||
<a class="header-anchor" href="#default-input-data" aria-hidden="true">#</a> Default input data</h3>
|
||||
<p>When the input data is null or undefined, updeep uses a empty plain object.</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">null,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">foo</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">bar</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">foo</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">bar</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h3 id="partial-application" tabindex="-1">
|
||||
<a class="header-anchor" href="#partial-application" aria-hidden="true">#</a> Partial application</h3>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> inc </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">i</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #C792EA">=></span><span style="color: #A6ACCD"> i </span><span style="color: #89DDFF">+</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> addOneYear </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> increment </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">addOneYear</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Shannon Barnes</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">62</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Shannon Barnes</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">63</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h2 id="u-freeze-datain" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-freeze-datain" aria-hidden="true">#</a> <code>u.freeze(dataIn)</code></h2>
|
||||
<p>Freeze your initial state to protect against mutations. Only performs the freezing in development, and returns the original object unchanged in production.</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> state </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">freeze</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">someKey</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Some Value</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">state</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">someKey </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Mutate</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">;</span><span style="color: #A6ACCD"> </span><span style="color: #676E95">// ERROR in development</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h2 id="u-updatein-datain-path-value" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-updatein-datain-path-value" aria-hidden="true">#</a> <code>u.updateIn(dataIn, path, value)</code></h2>
|
||||
<p>Update a single value with a simple string or array path. Can be use to update nested objects, arrays, or a combination. Can also be used to update every element of a nested array with <code>'*'</code>.</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">updateIn</span><span style="color: #A6ACCD">(</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">bunny</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">color</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">black</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">bunny.color</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">brown</span><span style="color: #89DDFF">"</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">bunny</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">color</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">brown</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">updateIn</span><span style="color: #A6ACCD">(</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">0.1.color</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">brown</span><span style="color: #89DDFF">"</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">)([[</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">color</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">blue</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">color</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">red</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> []])</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">([[</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">color</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">blue</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">color</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">brown</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> []])</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> incr </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">i</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #C792EA">=></span><span style="color: #A6ACCD"> i </span><span style="color: #89DDFF">+</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">updateIn</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">bunny.age</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> incr)(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">bunny</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">2</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">bunny</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">pets</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">bunny</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">2</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">] </span><span style="color: #89DDFF">}</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">pets</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">updateIn</span><span style="color: #A6ACCD">([</span><span style="color: #F78C6C">0</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">bunny</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">age</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD">) </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">pets</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">bunny</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">] </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">updateIn</span><span style="color: #A6ACCD">(</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">todos.*.done</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">true</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">)(</span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">todos</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">false</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">todos</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">true</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">done</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #FF9CAC">true</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h2 id="u-constant-datain" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-constant-datain" aria-hidden="true">#</a> <code>u.constant(dataIn)</code></h2>
|
||||
<p>Sometimes, you want to replace an object outright rather than merging it.
|
||||
You'll need to use a function that returns the new object.
|
||||
<code>u.constant</code> creates that function for you.</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> user </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Mitch</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">favorites</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">band</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Nirvana</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">movie</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">The Matrix</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> newFavorites </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">band</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Coldplay</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(user</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">favorites</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">constant</span><span style="color: #A6ACCD">(newFavorites) </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Mitch</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">favorites</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">band</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Coldplay</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> alwaysFour </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">constant</span><span style="color: #A6ACCD">(</span><span style="color: #F78C6C">4</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(</span><span style="color: #82AAFF">alwaysFour</span><span style="color: #A6ACCD">(</span><span style="color: #F78C6C">32</span><span style="color: #A6ACCD">))</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #F78C6C">4</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h2 id="u-if-datain-predicate-updates" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-if-datain-predicate-updates" aria-hidden="true">#</a> <code>u.if(dataIn, predicate, updates)</code></h2>
|
||||
<p>Apply <code>updates</code> if <code>predicate</code> is truthy, or if <code>predicate</code> is a function.
|
||||
It evaluates to truthy when called with <code>object</code>.</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #C792EA">function</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">isEven</span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">x</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #F07178"> </span><span style="color: #89DDFF">return</span><span style="color: #F07178"> </span><span style="color: #A6ACCD">x</span><span style="color: #F07178"> </span><span style="color: #89DDFF">%</span><span style="color: #F07178"> </span><span style="color: #F78C6C">2</span><span style="color: #F07178"> </span><span style="color: #89DDFF">===</span><span style="color: #F07178"> </span><span style="color: #F78C6C">0</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">}</span></span>
|
||||
<span class="line"><span style="color: #C792EA">function</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">increment</span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">x</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #F07178"> </span><span style="color: #89DDFF">return</span><span style="color: #F07178"> </span><span style="color: #A6ACCD">x</span><span style="color: #F07178"> </span><span style="color: #89DDFF">+</span><span style="color: #F07178"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">}</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> result </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">value</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">2</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">value</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">if</span><span style="color: #A6ACCD">(isEven</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> increment) </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #82AAFF">expect</span><span style="color: #A6ACCD">(result)</span><span style="color: #89DDFF">.</span><span style="color: #A6ACCD">to</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">eql</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">value</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h2 id="u-filter-arrayin-predicate" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-filter-arrayin-predicate" aria-hidden="true">#</a> <code>u.filter(arrayIn, predicate)</code></h2>
|
||||
<h2 id="u-reject-arrayin-predicate" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-reject-arrayin-predicate" aria-hidden="true">#</a> <code>u.reject(arrayIn, predicate)</code></h2>
|
||||
<h2 id="u-pickby-objectin-predicate" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-pickby-objectin-predicate" aria-hidden="true">#</a> <code>u.pickBy(objectIn, predicate)</code></h2>
|
||||
<h2 id="u-omitby-objectin-predicate" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-omitby-objectin-predicate" aria-hidden="true">#</a> <code>u.omitBy(objectIn, predicate)</code></h2>
|
||||
<h2 id="u-pick-objectin-keys" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-pick-objectin-keys" aria-hidden="true">#</a> <code>u.pick(objectIn, keys)</code></h2>
|
||||
<h2 id="u-omit-objectin-keys" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-omit-objectin-keys" aria-hidden="true">#</a> <code>u.omit(objectIn, keys)</code></h2>
|
||||
<p>Essentially the same as their Remeda counterparts. The difference being
|
||||
that if the transformation results in no change, the original object/array is
|
||||
returned.</p>
|
||||
<h2 id="u-matches-datain-condition" tabindex="-1">
|
||||
<a class="header-anchor" href="#u-matches-datain-condition" aria-hidden="true">#</a> <code>u.matches(dataIn, condition)</code></h2>
|
||||
<p>Do a deep comparison with <code>condition</code>, and returns
|
||||
<code>true</code> if the <code>dataIn</code> object matches.</p>
|
||||
<p>Scalar values are verified for equality (i.e., <code>{foo: 12}</code>
|
||||
will verify that the object has the prop <code>foo</code> set to <code>12</code>), and
|
||||
functions are going to be invoked with the object value of the object and
|
||||
expected to return <code>true</code> upon matching.</p>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #A6ACCD">u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">matches</span><span style="color: #A6ACCD">(</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Bob</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">32</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">address</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">...</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Bob</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">age</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #C792EA">=></span><span style="color: #A6ACCD"> age </span><span style="color: #89DDFF">></span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">30</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span><span style="color: #A6ACCD"> </span><span style="color: #676E95">// true</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div></article>
|
||||
|
||||
<hr class="border-gray-divider mt-20">
|
||||
|
||||
<div class="992:text-xl flex items-center pt-12 pb-20 text-lg font-semibold text-gray-300"><div class="mb-4 flex flex-col items-start"><span class="text-gray-inverse ml-3 mb-4 inline-block">Previous</span>
|
||||
|
||||
<a class="group transform-gpu text-lg font-medium transition-transform hover:scale-105 hover:text-gray-inverse" href="/latest/get-started" data-sveltekit-prefetch><span class="opacity-0 transition-opacity duration-100 group-hover:visible group-hover:opacity-100 inline-block"><-</span>
|
||||
<span class="inline-block transform transition-transform duration-100 group-hover:translate-x-0 -translate-x-3 ">Get started</span>
|
||||
</a></div>
|
||||
|
||||
</div>
|
||||
|
||||
</main>
|
||||
|
||||
<div class="992:flex-1"></div>
|
||||
|
||||
<div class="on-this-page pt-8 pb-8 hidden overflow-auto min-w-[160px] sticky right-4 pr-4 1440:right-6 1440:pr-2 1280:block pl-0.5 top-[var(--kd--navbar-height)] max-h-[calc(100vh-var(--kd--navbar-height))]" style=""><h5 class="font-semibold w-full text-left text-gray-inverse text-lg">On this page</h5>
|
||||
<ul class="space-y-4 mt-4"><li class="text-gray-soft hover:text-gray-inverse"><a href="#importing">Importing</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-datain-updates">u(dataIn, updates)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-update-datain-updates">u.update(dataIn, updates)</a></li>
|
||||
<ul class="space-y-3"><li class="flex group group text-gray-soft hover:text-gray-inverse"><svg viewBox="0 0 24 24" width="20" height="20" class="mr-px mt-px text-gray-300 dark:text-gray-400 group-hover:text-gray-soft"><!-- HTML_TAG_START --><path fill="currentColor" d="M12.172 12L9.343 9.172l1.414-1.415L15 12l-4.243 4.243l-1.414-1.415z"/><!-- HTML_TAG_END --></svg>
|
||||
<a href="#simple-update">Simple update</a>
|
||||
</li><li class="flex group group text-gray-soft hover:text-gray-inverse"><svg viewBox="0 0 24 24" width="20" height="20" class="mr-px mt-px text-gray-300 dark:text-gray-400 group-hover:text-gray-soft"><!-- HTML_TAG_START --><path fill="currentColor" d="M12.172 12L9.343 9.172l1.414-1.415L15 12l-4.243 4.243l-1.414-1.415z"/><!-- HTML_TAG_END --></svg>
|
||||
<a href="#multiple-updates">Multiple updates</a>
|
||||
</li><li class="flex group group text-gray-soft hover:text-gray-inverse"><svg viewBox="0 0 24 24" width="20" height="20" class="mr-px mt-px text-gray-300 dark:text-gray-400 group-hover:text-gray-soft"><!-- HTML_TAG_START --><path fill="currentColor" d="M12.172 12L9.343 9.172l1.414-1.415L15 12l-4.243 4.243l-1.414-1.415z"/><!-- HTML_TAG_END --></svg>
|
||||
<a href="#use-a-function">Use a function</a>
|
||||
</li><li class="flex group group text-gray-soft hover:text-gray-inverse"><svg viewBox="0 0 24 24" width="20" height="20" class="mr-px mt-px text-gray-300 dark:text-gray-400 group-hover:text-gray-soft"><!-- HTML_TAG_START --><path fill="currentColor" d="M12.172 12L9.343 9.172l1.414-1.415L15 12l-4.243 4.243l-1.414-1.415z"/><!-- HTML_TAG_END --></svg>
|
||||
<a href="#array-manipulation">Array Manipulation</a>
|
||||
</li><li class="flex group group text-gray-soft hover:text-gray-inverse"><svg viewBox="0 0 24 24" width="20" height="20" class="mr-px mt-px text-gray-300 dark:text-gray-400 group-hover:text-gray-soft"><!-- HTML_TAG_START --><path fill="currentColor" d="M12.172 12L9.343 9.172l1.414-1.415L15 12l-4.243 4.243l-1.414-1.415z"/><!-- HTML_TAG_END --></svg>
|
||||
<a href="#default-input-data">Default input data</a>
|
||||
</li><li class="flex group group text-gray-soft hover:text-gray-inverse"><svg viewBox="0 0 24 24" width="20" height="20" class="mr-px mt-px text-gray-300 dark:text-gray-400 group-hover:text-gray-soft"><!-- HTML_TAG_START --><path fill="currentColor" d="M12.172 12L9.343 9.172l1.414-1.415L15 12l-4.243 4.243l-1.414-1.415z"/><!-- HTML_TAG_END --></svg>
|
||||
<a href="#partial-application">Partial application</a>
|
||||
</li>
|
||||
</ul><li class="text-gray-soft hover:text-gray-inverse"><a href="#u-freeze-datain">u.freeze(dataIn)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-updatein-datain-path-value">u.updateIn(dataIn, path, value)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-constant-datain">u.constant(dataIn)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-if-datain-predicate-updates">u.if(dataIn, predicate, updates)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-filter-arrayin-predicate">u.filter(arrayIn, predicate)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-reject-arrayin-predicate">u.reject(arrayIn, predicate)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-pickby-objectin-predicate">u.pickBy(objectIn, predicate)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-omitby-objectin-predicate">u.omitBy(objectIn, predicate)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-pick-objectin-keys">u.pick(objectIn, keys)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-omit-objectin-keys">u.omit(objectIn, keys)</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#u-matches-datain-condition">u.matches(dataIn, condition)</a></li>
|
||||
</ul></div></div></div>
|
||||
|
||||
|
||||
<script type="module" data-sveltekit-hydrate="1ts6po4">
|
||||
import { start } from "../_app/immutable/start-4894d21d.js";
|
||||
|
||||
start({
|
||||
env: {},
|
||||
paths: {"base":"","assets":""},
|
||||
target: document.querySelector('[data-sveltekit-hydrate="1ts6po4"]').parentNode,
|
||||
version: "1673374967075",
|
||||
hydrate: {
|
||||
node_ids: [0, 4],
|
||||
data: [null,null],
|
||||
form: null
|
||||
}
|
||||
});
|
||||
</script>
|
||||
<script type="application/json" data-sveltekit-fetched data-url="/kit-docs/latest_api.meta">{"status":200,"statusText":"","headers":{},"body":"{\"excerpt\":\"\",\"headers\":[{\"level\":2,\"title\":\"Importing\",\"slug\":\"importing\",\"children\":[]},{\"level\":2,\"title\":\"u(dataIn, updates)\",\"slug\":\"u-datain-updates\",\"children\":[]},{\"level\":2,\"title\":\"u.update(dataIn, updates)\",\"slug\":\"u-update-datain-updates\",\"children\":[{\"level\":3,\"title\":\"Simple update\",\"slug\":\"simple-update\",\"children\":[]},{\"level\":3,\"title\":\"Multiple updates\",\"slug\":\"multiple-updates\",\"children\":[]},{\"level\":3,\"title\":\"Use a function\",\"slug\":\"use-a-function\",\"children\":[]},{\"level\":3,\"title\":\"Array Manipulation\",\"slug\":\"array-manipulation\",\"children\":[]},{\"level\":3,\"title\":\"Default input data\",\"slug\":\"default-input-data\",\"children\":[]},{\"level\":3,\"title\":\"Partial application\",\"slug\":\"partial-application\",\"children\":[]}]},{\"level\":2,\"title\":\"u.freeze(dataIn)\",\"slug\":\"u-freeze-datain\",\"children\":[]},{\"level\":2,\"title\":\"u.updateIn(dataIn, path, value)\",\"slug\":\"u-updatein-datain-path-value\",\"children\":[]},{\"level\":2,\"title\":\"u.constant(dataIn)\",\"slug\":\"u-constant-datain\",\"children\":[]},{\"level\":2,\"title\":\"u.if(dataIn, predicate, updates)\",\"slug\":\"u-if-datain-predicate-updates\",\"children\":[]},{\"level\":2,\"title\":\"u.filter(arrayIn, predicate)\",\"slug\":\"u-filter-arrayin-predicate\",\"children\":[]},{\"level\":2,\"title\":\"u.reject(arrayIn, predicate)\",\"slug\":\"u-reject-arrayin-predicate\",\"children\":[]},{\"level\":2,\"title\":\"u.pickBy(objectIn, predicate)\",\"slug\":\"u-pickby-objectin-predicate\",\"children\":[]},{\"level\":2,\"title\":\"u.omitBy(objectIn, predicate)\",\"slug\":\"u-omitby-objectin-predicate\",\"children\":[]},{\"level\":2,\"title\":\"u.pick(objectIn, keys)\",\"slug\":\"u-pick-objectin-keys\",\"children\":[]},{\"level\":2,\"title\":\"u.omit(objectIn, keys)\",\"slug\":\"u-omit-objectin-keys\",\"children\":[]},{\"level\":2,\"title\":\"u.matches(dataIn, condition)\",\"slug\":\"u-matches-datain-condition\",\"children\":[]}],\"title\":\"API\",\"frontmatter\":{\"title\":\"API\"},\"lastUpdated\":1673371541420}"}</script></div>
|
||||
</body>
|
||||
</html>
|
@ -1,14 +1,12 @@
|
||||
---
|
||||
title: API
|
||||
---
|
||||
|
||||
# API
|
||||
|
||||
:::info
|
||||
<div class="info">
|
||||
<h4>💡 Info</h4>
|
||||
|
||||
All functions are curried, Remeda-style, so if you see `f(dataIn, ...others)`, it can be called with either `f(dataIn, ...others)` or `f(...others)(dataIn)`.
|
||||
|
||||
:::
|
||||
</div>
|
||||
|
||||
## Importing
|
||||
|
@ -1,256 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<link rel="icon" href="../favicon.png" />
|
||||
<meta name="viewport" content="width=device-width" />
|
||||
|
||||
<script>
|
||||
const key = 'svelteness::color-scheme';
|
||||
const scheme = localStorage[key];
|
||||
const prefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches;
|
||||
if (scheme === 'dark' || (scheme !== 'light' && prefersDark)) {
|
||||
document.documentElement.classList.add('dark');
|
||||
} else {
|
||||
document.documentElement.classList.remove('dark');
|
||||
}
|
||||
</script>
|
||||
|
||||
<meta http-equiv="content-security-policy" content="">
|
||||
<link href="../_app/immutable/assets/_layout-d4f4ab95.css" rel="stylesheet">
|
||||
<link href="../_app/immutable/assets/Info-eb9b7651.css" rel="stylesheet">
|
||||
<link rel="modulepreload" href="../_app/immutable/start-4894d21d.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/singletons-79165f10.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/control-f5b05b5f.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/components/pages/_layout.svelte-ac40f340.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/contexts-c54c563b.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/stores-1c9d0b64.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/modules/pages/_layout.js-82ef414d.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/_layout-32f74dae.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/components/pages/latest/get-started/_page.md-5c5fe5e6.js">
|
||||
<link rel="modulepreload" href="../_app/immutable/chunks/Info-8cb253a1.js">
|
||||
</head>
|
||||
<body data-sveltekit-preload-data="hover">
|
||||
<div style="display: contents">
|
||||
|
||||
|
||||
<div class="kit-docs bg-gray-body min-h-full min-w-full h-full transition-transform duration-150 ease-out" style="font-family: var(--kd-font-family-sans, inherit); --kd--navbar-height: calc(var(--kd-navbar-height) + var(--kd-breadcrumbs-height));"><div class="fixed top-0 z-30 w-full flex-none transform-gpu transition-transform duration-150 ease-out supports-backdrop-blur:bg-white/60 bg-gray-200/95 backdrop-blur dark:bg-gray-800/60 translate-y-0" style="border-bottom: var(--kd-navbar-border-bottom);"><div class="flex w-full flex-col items-center justify-center mx-auto max-w-[var(--kd-navbar-max-width)] p-[var(--kd-navbar-padding)] h-[var(--kd--navbar-height)]"><div class="flex w-full items-center">
|
||||
|
||||
|
||||
<div class="flex-1"></div>
|
||||
|
||||
<div class="992:hidden -mr-2 flex items-center">
|
||||
|
||||
<div class="relative inline-block text-left not-prose"><button id="popover-button-2" type="button" class="inline-flex w-full justify-center rounded-md p-2 text-lg font-medium text-gray-soft hover:text-gray-inverse" aria-controls="popover-2" aria-expanded="false" aria-haspopup="true"><svg viewBox="0 0 24 24" width="30" height="30"><!-- HTML_TAG_START --><path fill="currentColor" d="M18 18v2H6v-2h12zm3-7v2H3v-2h18zm-3-7v2H6V4h12z"/><!-- HTML_TAG_END --></svg>
|
||||
<span class="sr-only">Main navigation menu</span>
|
||||
</button>
|
||||
|
||||
<div class="fixed top-0 left-0 bg-black/40 backdrop-blur-sm dark:bg-gray-700/80 transition-opacity duration-75 pointer-events-auto z-40 w-screen h-screen opacity-0 invisible"></div>
|
||||
|
||||
<div hidden></div>
|
||||
|
||||
</div></div>
|
||||
|
||||
<div class="992:flex 992:items-center hidden"><nav><ul class="flex items-center space-x-8 text-lg font-medium"><li class="mt-4 first:mt-0 992:mt-0"><a class="p-1 border-b hover:border-b-2 border-brand text-gray-inverse" href="/latest/get-started">Get started</a></li><li class="mt-4 first:mt-0 992:mt-0"><a class="p-1 text-gray-soft hover:text-gray-inverse" href="/latest/api">API</a></li></ul></nav>
|
||||
|
||||
|
||||
|
||||
|
||||
<div class="border-gray-divider ml-6 mr-2.5 h-7 w-2 border-l-[1.5px]"></div>
|
||||
|
||||
<div class="hidden 992:flex items-center">
|
||||
|
||||
<div class="relative inline-block text-left not-prose"><button id="menu-button-2" type="button" class="inline-flex w-full justify-center rounded-md p-2 text-lg font-medium text-gray-soft hover:text-gray-inverse" aria-controls="menu-2" aria-expanded="false" aria-haspopup="true"><svg viewBox="0 0 24 24" width="1.2em" height="1.2em" class="h-6 w-6"><!-- HTML_TAG_START --><path fill="currentColor" d="M12 18a6 6 0 1 1 0-12a6 6 0 0 1 0 12zM11 1h2v3h-2V1zm0 19h2v3h-2v-3zM3.515 4.929l1.414-1.414L7.05 5.636L5.636 7.05L3.515 4.93zM16.95 18.364l1.414-1.414l2.121 2.121l-1.414 1.414l-2.121-2.121zm2.121-14.85l1.414 1.415l-2.121 2.121l-1.414-1.414l2.121-2.121zM5.636 16.95l1.414 1.414l-2.121 2.121l-1.414-1.414l2.121-2.121zM23 11v2h-3v-2h3zM4 11v2H1v-2h3z"/><!-- HTML_TAG_END --></svg>
|
||||
<span class="sr-only">Color Scheme</span>
|
||||
</button>
|
||||
|
||||
<div hidden></div>
|
||||
|
||||
</div></div></div></div>
|
||||
|
||||
<div class="border-gray-divider 992:hidden flex w-full items-center mt-4 pt-4 border-t"><button id="main-sidebar-button" type="button" class="text-gray-soft hover:text-gray-inverse inline-flex justify-center rounded-md p-2 text-sm font-medium" aria-controls="main-sidebar" aria-expanded="false" aria-haspopup="true"><span class="sr-only">Open main sidebar</span>
|
||||
<svg viewBox="0 0 24 24" width="28" height="28"><!-- HTML_TAG_START --><path fill="currentColor" d="M21 18v2H3v-2h18zM17.05 3.55L22 8.5l-4.95 4.95v-9.9zM12 11v2H3v-2h9zm0-7v2H3V4h9z"/><!-- HTML_TAG_END --></svg></button>
|
||||
|
||||
<ol class="text-md text-gray-soft flex items-center whitespace-nowrap leading-6 mt-px ml-2.5">
|
||||
<li class="truncate font-semibold text-slate-900 dark:text-slate-200">Get started</li></ol></div>
|
||||
|
||||
|
||||
</div></div>
|
||||
|
||||
<div class="mx-auto w-full flex flex-row min-h-full max-w-[var(--kd-content-max-width)] pt-[var(--kd--navbar-height)] z-20"><aside id="main-sidebar" class="sidebar self-start fixed top-0 left-0 transform bg-gray-body z-50 border-gray-divider border-r -translate-x-full transform transition-transform duration-200 ease-out will-change-transform max-h-screen min-h-screen min-w-[var(--kd-sidebar-min-width)] max-w-[var(--kd-sidebar-max-width)] 992:translate-x-0 922:block 992:sticky 992:z-0 overflow-y-auto p-[var(--kd-sidebar-padding)] 992:top-[var(--kd--navbar-height)] 992:min-h-[calc(100vh-var(--kd--navbar-height))] 992:max-h-[calc(100vh-var(--kd--navbar-height))]" role="dialog" aria-modal="true" style=""><div class="992:hidden sticky top-0 left-0 flex items-center"><div class="flex-1"></div>
|
||||
<button class="text-gray-soft hover:text-gray-inverse p-4 -mx-6 pointer-events-none"><svg viewBox="0 0 24 24" width="24" height="24"><!-- HTML_TAG_START --><path fill="currentColor" d="m12 10.586l4.95-4.95l1.414 1.414l-4.95 4.95l4.95 4.95l-1.414 1.414l-4.95-4.95l-4.95 4.95l-1.414-1.414l4.95-4.95l-4.95-4.95L7.05 5.636z"/><!-- HTML_TAG_END --></svg>
|
||||
<span class="sr-only">Close sidebar</span></button></div>
|
||||
|
||||
<nav class="992:px-1">
|
||||
|
||||
|
||||
|
||||
<ul class="mt-8 pb-28 992:pb-0">
|
||||
<li class="992:mt-10 mt-12 first:mt-0"><h5 class="text-gray-strong 992:mb-3 mb-8 text-lg font-semibold">
|
||||
</h5>
|
||||
<ul class="border-gray-divider space-y-3 border-l"><li class="first:mt-6"><a class="992:py-1.5 -ml-px flex items-center border-l-2 py-2 pl-4 text-brand font-semibold" href="/latest/get-started" style="border-color: var(--kd-sidebar-border-active);">
|
||||
Get started
|
||||
</a>
|
||||
</li><li class="first:mt-6"><a class="992:py-1.5 -ml-px flex items-center border-l-2 py-2 pl-4 hover:border-gray-inverse text-gray-soft hover:text-gray-inverse border-transparent font-normal" href="/latest/api" style="">
|
||||
API
|
||||
</a>
|
||||
</li></ul>
|
||||
</li></ul>
|
||||
|
||||
|
||||
</nav></aside>
|
||||
|
||||
<div class="992:hidden z-40"><div class="fixed top-0 left-0 bg-black/40 backdrop-blur-sm dark:bg-gray-700/80 transition-opacity duration-75 pointer-events-auto z-40 w-screen h-screen opacity-0 invisible"></div></div>
|
||||
|
||||
<main class="w-full overflow-x-hidden 992:min-h-[calc(100vh-var(--kd--navbar-height))] min-h-[calc(100vh-var(--kd--navbar-height))] px-8 992:px-16 pt-8" style="max-width: var(--kd-main-max-width, var(--kd-article-max-width));">
|
||||
|
||||
<article class="markdown prose dark:prose-invert z-10 max-w-[var(--kd-article-max-width)]">
|
||||
|
||||
<h1>updeep-remeda</h1>
|
||||
<blockquote><p>Easily update nested frozen objects and arrays in a declarative and immutable
|
||||
manner.</p></blockquote>
|
||||
<h2 id="about" tabindex="-1">
|
||||
<a class="header-anchor" href="#about" aria-hidden="true">#</a> About</h2>
|
||||
<div class="svelte-ns3bhs"><h4 class="svelte-ns3bhs">💡 Info</h4>
|
||||
|
||||
<p>This is a fork of the main updeep package. For ease of reading — not to
|
||||
mention ease of shamelessly lifting large pieces of the original
|
||||
documentation — in this documentation all mentions of <code>updeep</code> refers to this
|
||||
fork.</p>
|
||||
|
||||
</div>
|
||||
<p>updeep makes updating deeply nested objects/arrays painless by allowing you to
|
||||
declare the updates you would like to make and it will take care of the rest. It
|
||||
will recursively return the same instance if no changes have been made, making
|
||||
it ideal for using reference equality checks to detect changes.</p>
|
||||
<p>Because of this, everything returned by updeep is frozen. Not only that, but
|
||||
updeep assumes that every object passed in to update is immutable, so it may
|
||||
freeze objects passed in as well. Note that the freezing only happens in
|
||||
development.</p>
|
||||
<p>This fork of updeep requires Remeda, but works very well with any other utility function ([lodash], [Ramda], etc).</p>
|
||||
<h2 id="differences-with-the-original-updeep" tabindex="-1">
|
||||
<a class="header-anchor" href="#differences-with-the-original-updeep" aria-hidden="true">#</a> Differences with the original Updeep</h2>
|
||||
<ul><li><p>Under the hood, the use of lodash has
|
||||
been replaced by Remeda (for better type support and tree-shaking abilities).</p></li>
|
||||
<li><p>The codebase has been ported to TypeScript (mostly for the lulz).</p></li>
|
||||
<li><p>The order of parameters in the non-curryied invocation of functions has been modified. In the original updeep the input object is the last parameter, whereas here it's the first.</p></li></ul>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #676E95">// original updeep</span></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> dataIn </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">a</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">b</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">2</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">let</span><span style="color: #A6ACCD"> dataOut </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">c</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span><span style="color: #A6ACCD"> dataIn)</span><span style="color: #89DDFF">;</span><span style="color: #A6ACCD"> </span><span style="color: #676E95">// simple call</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">dataOut </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">c</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)(dataIn)</span><span style="color: #89DDFF">;</span><span style="color: #A6ACCD"> </span><span style="color: #676E95">// curried</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #676E95">// updeep-remeda</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">dataOut </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(dataIn</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">c</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span><span style="color: #A6ACCD"> </span><span style="color: #676E95">// simple call</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">dataOut </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">c</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">3</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)(dataIn)</span><span style="color: #89DDFF">;</span><span style="color: #A6ACCD"> </span><span style="color: #676E95">// curried</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><ul><li><p><code>withDefault</code> has been removed as the behavior can be implemented using
|
||||
Remeda's <code>pipe</code>, or a simple <code>??</code>.</p></li>
|
||||
<li><p><code>u.omitted</code> has been renamed <code>u.skip</code>.</p></li></ul>
|
||||
<h2 id="installation" tabindex="-1">
|
||||
<a class="header-anchor" href="#installation" aria-hidden="true">#</a> Installation</h2>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-bash ext-sh" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #A6ACCD">$ npm install @yanick/updeep-remeda</span></span>
|
||||
<span class="line"><span style="color: #676E95"># or</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD">$ pnpm install @yanick/updeep-remeda</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div><h2 id="full-example" tabindex="-1">
|
||||
<a class="header-anchor" href="#full-example" aria-hidden="true">#</a> Full example</h2>
|
||||
<div class="code-fence overflow-y-auto relative max-h-[60vh] 576:max-h-[32rem] my-8 rounded-md shadow-lg mx-auto border border-gray-divider lang-javascript ext-js" style="background-color: var(--kd-code-fence-bg);">
|
||||
|
||||
<div class="code relative z-0 overflow-hidden"><div class=""><!-- HTML_TAG_START --><pre><code><span class="line"><span style="color: #89DDFF">import</span><span style="color: #A6ACCD"> u </span><span style="color: #89DDFF">from</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">@yanick/updeep-remeda</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> person </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">first</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Bill</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">last</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Sagat</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">children</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Mary-Kate</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">7</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Ashley</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">7</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> ]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">todo</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> [</span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Be funny</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Manage household</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD">]</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">email</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">bill@example.com</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">version</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">};</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> inc </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">i</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #C792EA">=></span><span style="color: #A6ACCD"> i </span><span style="color: #89DDFF">+</span><span style="color: #A6ACCD"> </span><span style="color: #F78C6C">1</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> eq </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">x</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #C792EA">=></span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">(</span><span style="color: #A6ACCD">y</span><span style="color: #89DDFF">)</span><span style="color: #A6ACCD"> </span><span style="color: #C792EA">=></span><span style="color: #A6ACCD"> x </span><span style="color: #89DDFF">===</span><span style="color: #A6ACCD"> y</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"></span>
|
||||
<span class="line"><span style="color: #C792EA">const</span><span style="color: #A6ACCD"> newPerson </span><span style="color: #89DDFF">=</span><span style="color: #A6ACCD"> </span><span style="color: #82AAFF">u</span><span style="color: #A6ACCD">(person</span><span style="color: #89DDFF">,</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span></span>
|
||||
<span class="line"><span style="color: #89DDFF"> </span><span style="color: #676E95">// Change first name</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">name</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">first</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Bob</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">},</span></span>
|
||||
<span class="line"><span style="color: #89DDFF"> </span><span style="color: #676E95">// Increment all children's ages</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">children</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">map</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">{</span><span style="color: #A6ACCD"> </span><span style="color: #F07178">age</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> inc </span><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF"> </span><span style="color: #676E95">// Update email</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">email</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> </span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">bob@example.com</span><span style="color: #89DDFF">"</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF"> </span><span style="color: #676E95">// Remove todo</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">todo</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> u</span><span style="color: #89DDFF">.</span><span style="color: #82AAFF">reject</span><span style="color: #A6ACCD">(</span><span style="color: #82AAFF">eq</span><span style="color: #A6ACCD">(</span><span style="color: #89DDFF">"</span><span style="color: #C3E88D">Be funny</span><span style="color: #89DDFF">"</span><span style="color: #A6ACCD">))</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF"> </span><span style="color: #676E95">// Increment version</span></span>
|
||||
<span class="line"><span style="color: #A6ACCD"> </span><span style="color: #F07178">version</span><span style="color: #89DDFF">:</span><span style="color: #A6ACCD"> inc</span><span style="color: #89DDFF">,</span></span>
|
||||
<span class="line"><span style="color: #89DDFF">}</span><span style="color: #A6ACCD">)</span><span style="color: #89DDFF">;</span></span>
|
||||
<span class="line"><span style="color: #676E95">// => {</span></span>
|
||||
<span class="line"><span style="color: #676E95">// name: { first: 'Bob', last: 'Sagat' },</span></span>
|
||||
<span class="line"><span style="color: #676E95">// children: [</span></span>
|
||||
<span class="line"><span style="color: #676E95">// { name: 'Mary-Kate', age: 8 },</span></span>
|
||||
<span class="line"><span style="color: #676E95">// { name: 'Ashley', age: 8 }</span></span>
|
||||
<span class="line"><span style="color: #676E95">// ],</span></span>
|
||||
<span class="line"><span style="color: #676E95">// todo: [</span></span>
|
||||
<span class="line"><span style="color: #676E95">// 'Manage household'</span></span>
|
||||
<span class="line"><span style="color: #676E95">// ],</span></span>
|
||||
<span class="line"><span style="color: #676E95">// email: 'bob@example.com',</span></span>
|
||||
<span class="line"><span style="color: #676E95">// version: 2</span></span>
|
||||
<span class="line"><span style="color: #676E95">//}</span></span>
|
||||
<span class="line"></span></code></pre><!-- HTML_TAG_END --></div>
|
||||
|
||||
|
||||
|
||||
</div></div></article>
|
||||
|
||||
<hr class="border-gray-divider mt-20">
|
||||
|
||||
<div class="992:text-xl flex items-center pt-12 pb-20 text-lg font-semibold text-gray-300">
|
||||
|
||||
<div class="ml-auto mb-4 flex flex-col items-end"><span class="text-gray-inverse mr-3 mb-4 inline-block">Next</span>
|
||||
|
||||
<a class="group transform-gpu text-lg font-medium transition-transform hover:scale-105 hover:text-gray-inverse" href="/latest/api" data-sveltekit-prefetch>
|
||||
<span class="inline-block transform transition-transform duration-100 group-hover:translate-x-0 translate-x-2">API</span>
|
||||
<span class="opacity-0 transition-opacity duration-100 group-hover:visible group-hover:opacity-100 inline-block">-></span></a></div></div>
|
||||
|
||||
</main>
|
||||
|
||||
<div class="992:flex-1"></div>
|
||||
|
||||
<div class="on-this-page pt-8 pb-8 hidden overflow-auto min-w-[160px] sticky right-4 pr-4 1440:right-6 1440:pr-2 1280:block pl-0.5 top-[var(--kd--navbar-height)] max-h-[calc(100vh-var(--kd--navbar-height))]" style=""><h5 class="font-semibold w-full text-left text-gray-inverse text-lg">On this page</h5>
|
||||
<ul class="space-y-4 mt-4"><li class="text-gray-soft hover:text-gray-inverse"><a href="#about">About</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#differences-with-the-original-updeep">Differences with the original Updeep</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#installation">Installation</a></li>
|
||||
<li class="text-gray-soft hover:text-gray-inverse"><a href="#full-example">Full example</a></li>
|
||||
</ul></div></div></div>
|
||||
|
||||
|
||||
<script type="module" data-sveltekit-hydrate="13ln1h8">
|
||||
import { start } from "../_app/immutable/start-4894d21d.js";
|
||||
|
||||
start({
|
||||
env: {},
|
||||
paths: {"base":"","assets":""},
|
||||
target: document.querySelector('[data-sveltekit-hydrate="13ln1h8"]').parentNode,
|
||||
version: "1673374967075",
|
||||
hydrate: {
|
||||
node_ids: [0, 5],
|
||||
data: [null,null],
|
||||
form: null
|
||||
}
|
||||
});
|
||||
</script>
|
||||
<script type="application/json" data-sveltekit-fetched data-url="/kit-docs/latest_get-started.meta">{"status":200,"statusText":"","headers":{},"body":"{\"excerpt\":\"\",\"headers\":[{\"level\":2,\"title\":\"About\",\"slug\":\"about\",\"children\":[]},{\"level\":2,\"title\":\"Differences with the original Updeep\",\"slug\":\"differences-with-the-original-updeep\",\"children\":[]},{\"level\":2,\"title\":\"Installation\",\"slug\":\"installation\",\"children\":[]},{\"level\":2,\"title\":\"Full example\",\"slug\":\"full-example\",\"children\":[]}],\"title\":\"Get Started\",\"frontmatter\":{\"title\":\"Get Started\"},\"lastUpdated\":1673371541420}"}</script></div>
|
||||
</body>
|
||||
</html>
|
1
docs/vendor/docsify.js
vendored
Normal file
1
docs/vendor/docsify.js
vendored
Normal file
File diff suppressed because one or more lines are too long
1
docs/vendor/themes/vue.css
vendored
Normal file
1
docs/vendor/themes/vue.css
vendored
Normal file
File diff suppressed because one or more lines are too long
@ -1,214 +0,0 @@
|
||||
{
|
||||
"src/lib/fonts/Inter-VF.italic-latin.woff2": {
|
||||
"file": "_app/immutable/assets/Inter-VF.italic-latin-65279caf.woff2",
|
||||
"src": "src/lib/fonts/Inter-VF.italic-latin.woff2"
|
||||
},
|
||||
"src/lib/fonts/Inter-VF.roman-latin.woff2": {
|
||||
"file": "_app/immutable/assets/Inter-VF.roman-latin-1b58736b.woff2",
|
||||
"src": "src/lib/fonts/Inter-VF.roman-latin.woff2"
|
||||
},
|
||||
"src/lib/fonts/FiraCode-VF.woff2": {
|
||||
"file": "_app/immutable/assets/FiraCode-VF-05b30ba3.woff2",
|
||||
"src": "src/lib/fonts/FiraCode-VF.woff2"
|
||||
},
|
||||
"src/lib/fonts/FiraCode-VF.woff": {
|
||||
"file": "_app/immutable/assets/FiraCode-VF-71c5868a.woff",
|
||||
"src": "src/lib/fonts/FiraCode-VF.woff"
|
||||
},
|
||||
"Info.css": {
|
||||
"file": "_app/immutable/assets/Info-eb9b7651.css",
|
||||
"src": "Info.css"
|
||||
},
|
||||
"src/routes/+layout.css": {
|
||||
"file": "_app/immutable/assets/_layout-d4f4ab95.css",
|
||||
"src": "src/routes/+layout.css"
|
||||
},
|
||||
"_control-f5b05b5f.js": {
|
||||
"file": "_app/immutable/chunks/control-f5b05b5f.js"
|
||||
},
|
||||
"node_modules/.pnpm/@sveltejs+kit@1.0.7_svelte@3.55.0+vite@4.0.4/node_modules/@sveltejs/kit/src/runtime/components/error.svelte": {
|
||||
"file": "_app/immutable/components/error.svelte-884b4aac.js",
|
||||
"src": "node_modules/.pnpm/@sveltejs+kit@1.0.7_svelte@3.55.0+vite@4.0.4/node_modules/@sveltejs/kit/src/runtime/components/error.svelte",
|
||||
"isEntry": true,
|
||||
"imports": [
|
||||
"_singletons-79165f10.js",
|
||||
"_stores-1c9d0b64.js"
|
||||
]
|
||||
},
|
||||
"__layout-32f74dae.js": {
|
||||
"file": "_app/immutable/chunks/_layout-32f74dae.js"
|
||||
},
|
||||
"_index-35a671a5.js": {
|
||||
"file": "_app/immutable/chunks/index-35a671a5.js",
|
||||
"imports": [
|
||||
"_control-f5b05b5f.js"
|
||||
]
|
||||
},
|
||||
"__page-a27df1e4.js": {
|
||||
"file": "_app/immutable/chunks/_page-a27df1e4.js",
|
||||
"imports": [
|
||||
"_index-35a671a5.js"
|
||||
]
|
||||
},
|
||||
"_contexts-c54c563b.js": {
|
||||
"file": "_app/immutable/chunks/contexts-c54c563b.js",
|
||||
"imports": [
|
||||
"_singletons-79165f10.js",
|
||||
"_stores-1c9d0b64.js"
|
||||
]
|
||||
},
|
||||
"__page-115bdbbb.js": {
|
||||
"file": "_app/immutable/chunks/_page-115bdbbb.js",
|
||||
"imports": [
|
||||
"_index-35a671a5.js"
|
||||
]
|
||||
},
|
||||
".svelte-kit/generated/nodes/4.js": {
|
||||
"file": "_app/immutable/chunks/4-6a5c1f74.js",
|
||||
"src": ".svelte-kit/generated/nodes/4.js",
|
||||
"isDynamicEntry": true,
|
||||
"imports": [
|
||||
"src/routes/latest/api/+page.md"
|
||||
]
|
||||
},
|
||||
".svelte-kit/generated/nodes/2.js": {
|
||||
"file": "_app/immutable/chunks/2-c0299577.js",
|
||||
"src": ".svelte-kit/generated/nodes/2.js",
|
||||
"isDynamicEntry": true,
|
||||
"imports": [
|
||||
"__page-a27df1e4.js"
|
||||
]
|
||||
},
|
||||
".svelte-kit/generated/nodes/1.js": {
|
||||
"file": "_app/immutable/chunks/1-1bd08e4a.js",
|
||||
"src": ".svelte-kit/generated/nodes/1.js",
|
||||
"isDynamicEntry": true,
|
||||
"imports": [
|
||||
"node_modules/.pnpm/@sveltejs+kit@1.0.7_svelte@3.55.0+vite@4.0.4/node_modules/@sveltejs/kit/src/runtime/components/error.svelte"
|
||||
]
|
||||
},
|
||||
".svelte-kit/generated/nodes/3.js": {
|
||||
"file": "_app/immutable/chunks/3-c0299577.js",
|
||||
"src": ".svelte-kit/generated/nodes/3.js",
|
||||
"isDynamicEntry": true,
|
||||
"imports": [
|
||||
"__page-115bdbbb.js"
|
||||
]
|
||||
},
|
||||
"src/routes/+page.js": {
|
||||
"file": "_app/immutable/modules/pages/_page.js-c1f1be17.js",
|
||||
"src": "src/routes/+page.js",
|
||||
"isEntry": true,
|
||||
"imports": [
|
||||
"_index-35a671a5.js",
|
||||
"__page-a27df1e4.js"
|
||||
]
|
||||
},
|
||||
".svelte-kit/generated/nodes/0.js": {
|
||||
"file": "_app/immutable/chunks/0-0174d166.js",
|
||||
"src": ".svelte-kit/generated/nodes/0.js",
|
||||
"isDynamicEntry": true,
|
||||
"imports": [
|
||||
"__layout-32f74dae.js",
|
||||
"src/routes/+layout.svelte"
|
||||
]
|
||||
},
|
||||
"src/routes/+layout.js": {
|
||||
"file": "_app/immutable/modules/pages/_layout.js-82ef414d.js",
|
||||
"src": "src/routes/+layout.js",
|
||||
"isEntry": true,
|
||||
"imports": [
|
||||
"__layout-32f74dae.js"
|
||||
]
|
||||
},
|
||||
".svelte-kit/generated/nodes/5.js": {
|
||||
"file": "_app/immutable/chunks/5-2bf42e67.js",
|
||||
"src": ".svelte-kit/generated/nodes/5.js",
|
||||
"isDynamicEntry": true,
|
||||
"imports": [
|
||||
"src/routes/latest/get-started/+page.md"
|
||||
]
|
||||
},
|
||||
"_singletons-79165f10.js": {
|
||||
"file": "_app/immutable/chunks/singletons-79165f10.js"
|
||||
},
|
||||
"src/routes/latest/+page.js": {
|
||||
"file": "_app/immutable/modules/pages/latest/_page.js-bc157eed.js",
|
||||
"src": "src/routes/latest/+page.js",
|
||||
"isEntry": true,
|
||||
"imports": [
|
||||
"_index-35a671a5.js",
|
||||
"__page-115bdbbb.js"
|
||||
]
|
||||
},
|
||||
"_stores-1c9d0b64.js": {
|
||||
"file": "_app/immutable/chunks/stores-1c9d0b64.js",
|
||||
"imports": [
|
||||
"_singletons-79165f10.js"
|
||||
]
|
||||
},
|
||||
"src/routes/latest/get-started/+page.md": {
|
||||
"file": "_app/immutable/components/pages/latest/get-started/_page.md-5c5fe5e6.js",
|
||||
"src": "src/routes/latest/get-started/+page.md",
|
||||
"isEntry": true,
|
||||
"imports": [
|
||||
"_singletons-79165f10.js",
|
||||
"_Info-8cb253a1.js"
|
||||
]
|
||||
},
|
||||
"node_modules/.pnpm/@sveltejs+kit@1.0.7_svelte@3.55.0+vite@4.0.4/node_modules/@sveltejs/kit/src/runtime/client/start.js": {
|
||||
"file": "_app/immutable/start-4894d21d.js",
|
||||
"src": "node_modules/.pnpm/@sveltejs+kit@1.0.7_svelte@3.55.0+vite@4.0.4/node_modules/@sveltejs/kit/src/runtime/client/start.js",
|
||||
"isEntry": true,
|
||||
"imports": [
|
||||
"_singletons-79165f10.js",
|
||||
"_control-f5b05b5f.js"
|
||||
],
|
||||
"dynamicImports": [
|
||||
".svelte-kit/generated/nodes/0.js",
|
||||
".svelte-kit/generated/nodes/1.js",
|
||||
".svelte-kit/generated/nodes/2.js",
|
||||
".svelte-kit/generated/nodes/3.js",
|
||||
".svelte-kit/generated/nodes/4.js",
|
||||
".svelte-kit/generated/nodes/5.js"
|
||||
]
|
||||
},
|
||||
"src/routes/latest/api/+page.md": {
|
||||
"file": "_app/immutable/components/pages/latest/api/_page.md-bd91dac8.js",
|
||||
"src": "src/routes/latest/api/+page.md",
|
||||
"isEntry": true,
|
||||
"imports": [
|
||||
"_singletons-79165f10.js",
|
||||
"_Info-8cb253a1.js"
|
||||
]
|
||||
},
|
||||
"_Info-8cb253a1.js": {
|
||||
"file": "_app/immutable/chunks/Info-8cb253a1.js",
|
||||
"imports": [
|
||||
"_singletons-79165f10.js",
|
||||
"_contexts-c54c563b.js"
|
||||
],
|
||||
"css": [
|
||||
"_app/immutable/assets/Info-eb9b7651.css"
|
||||
]
|
||||
},
|
||||
"src/routes/+layout.svelte": {
|
||||
"file": "_app/immutable/components/pages/_layout.svelte-ac40f340.js",
|
||||
"src": "src/routes/+layout.svelte",
|
||||
"isEntry": true,
|
||||
"imports": [
|
||||
"_singletons-79165f10.js",
|
||||
"_contexts-c54c563b.js",
|
||||
"_stores-1c9d0b64.js"
|
||||
],
|
||||
"css": [
|
||||
"_app/immutable/assets/_layout-d4f4ab95.css"
|
||||
],
|
||||
"assets": [
|
||||
"_app/immutable/assets/Inter-VF.roman-latin-1b58736b.woff2",
|
||||
"_app/immutable/assets/Inter-VF.italic-latin-65279caf.woff2",
|
||||
"_app/immutable/assets/FiraCode-VF-05b30ba3.woff2",
|
||||
"_app/immutable/assets/FiraCode-VF-71c5868a.woff"
|
||||
]
|
||||
}
|
||||
}
|
10
website/.gitignore
vendored
10
website/.gitignore
vendored
@ -1,10 +0,0 @@
|
||||
.DS_Store
|
||||
node_modules
|
||||
/build
|
||||
/.svelte-kit
|
||||
/package
|
||||
.env
|
||||
.env.*
|
||||
!.env.example
|
||||
vite.config.js.timestamp-*
|
||||
vite.config.ts.timestamp-*
|
@ -1 +0,0 @@
|
||||
engine-strict=true
|
@ -1,38 +0,0 @@
|
||||
# create-svelte
|
||||
|
||||
Everything you need to build a Svelte project, powered by [`create-svelte`](https://github.com/sveltejs/kit/tree/master/packages/create-svelte).
|
||||
|
||||
## Creating a project
|
||||
|
||||
If you're seeing this, you've probably already done this step. Congrats!
|
||||
|
||||
```bash
|
||||
# create a new project in the current directory
|
||||
npm create svelte@latest
|
||||
|
||||
# create a new project in my-app
|
||||
npm create svelte@latest my-app
|
||||
```
|
||||
|
||||
## Developing
|
||||
|
||||
Once you've created a project and installed dependencies with `npm install` (or `pnpm install` or `yarn`), start a development server:
|
||||
|
||||
```bash
|
||||
npm run dev
|
||||
|
||||
# or start the server and open the app in a new browser tab
|
||||
npm run dev -- --open
|
||||
```
|
||||
|
||||
## Building
|
||||
|
||||
To create a production version of your app:
|
||||
|
||||
```bash
|
||||
npm run build
|
||||
```
|
||||
|
||||
You can preview the production build with `npm run preview`.
|
||||
|
||||
> To deploy your app, you may need to install an [adapter](https://kit.svelte.dev/docs/adapters) for your target environment.
|
@ -1,35 +0,0 @@
|
||||
{
|
||||
"name": "mydocs",
|
||||
"version": "0.0.1",
|
||||
"private": true,
|
||||
"scripts": {
|
||||
"dev": "vite dev",
|
||||
"build": "vite build",
|
||||
"preview": "vite preview"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@sveltejs/adapter-auto": "^1.0.0",
|
||||
"@sveltejs/kit": "^1.0.0",
|
||||
"svelte": "^3.54.0",
|
||||
"vite": "^4.0.0"
|
||||
},
|
||||
"type": "module",
|
||||
"dependencies": {
|
||||
"@iconify-json/ri": "^1.1.4",
|
||||
"@rollup/pluginutils": "^5.0.2",
|
||||
"@sveltejs/adapter-static": "^1.0.1",
|
||||
"@svelteness/kit-docs": "link:../../kit-docs/packages/kit-docs",
|
||||
"globby": "^13.1.3",
|
||||
"gray-matter": "^4.0.3",
|
||||
"kit-docs-workspace": "github:svelteness/kit-docs",
|
||||
"kleur": "^4.1.5",
|
||||
"lru-cache": "^7.14.1",
|
||||
"markdown-it": "^13.0.1",
|
||||
"markdown-it-anchor": "^8.6.6",
|
||||
"markdown-it-container": "^3.0.0",
|
||||
"markdown-it-emoji": "^2.0.2",
|
||||
"shiki": "^0.12.1",
|
||||
"toml": "^3.0.0",
|
||||
"unplugin-icons": "^0.15.1"
|
||||
}
|
||||
}
|
@ -1,24 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<link rel="icon" href="%sveltekit.assets%/favicon.png" />
|
||||
<meta name="viewport" content="width=device-width" />
|
||||
|
||||
<script>
|
||||
const key = 'svelteness::color-scheme';
|
||||
const scheme = localStorage[key];
|
||||
const prefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches;
|
||||
if (scheme === 'dark' || (scheme !== 'light' && prefersDark)) {
|
||||
document.documentElement.classList.add('dark');
|
||||
} else {
|
||||
document.documentElement.classList.remove('dark');
|
||||
}
|
||||
</script>
|
||||
|
||||
%sveltekit.head%
|
||||
</head>
|
||||
<body data-sveltekit-preload-data="hover">
|
||||
<div style="display: contents">%sveltekit.body%</div>
|
||||
</body>
|
||||
</html>
|
@ -1,24 +0,0 @@
|
||||
<div>
|
||||
|
||||
<h4>💡 Info</h4>
|
||||
|
||||
<slot/>
|
||||
|
||||
</div>
|
||||
|
||||
<style>
|
||||
div {
|
||||
background: lightgreen;
|
||||
margin: 0px 2em;
|
||||
padding: 0.25em 1em;
|
||||
font-weight: normal;
|
||||
border-radius: 1em;
|
||||
color: black;
|
||||
}
|
||||
|
||||
|
||||
h4 {
|
||||
margin: 0px;
|
||||
}
|
||||
|
||||
</style>
|
@ -1,401 +0,0 @@
|
||||
import { type FilterPattern, createFilter } from '@rollup/pluginutils';
|
||||
import { json, RequestHandler } from '@sveltejs/kit';
|
||||
import { readFileSync } from 'fs';
|
||||
import { globbySync } from 'globby';
|
||||
import kleur from 'kleur';
|
||||
import path from 'path';
|
||||
|
||||
import {
|
||||
type MarkdownParser,
|
||||
type ParsedMarkdownResult,
|
||||
createMarkdownParser,
|
||||
getFrontmatter,
|
||||
parseMarkdown,
|
||||
} from '../markdown-plugin/parser';
|
||||
import { readDirDeepSync, sortOrderedFiles } from '../utils/fs';
|
||||
import { kebabToTitleCase } from '../utils/string';
|
||||
import { isString } from '../utils/unit';
|
||||
|
||||
const CWD = process.cwd();
|
||||
const ROUTES_DIR = path.resolve(CWD, 'src/routes');
|
||||
|
||||
let parser: MarkdownParser;
|
||||
|
||||
const restParamsRE = /\[\.\.\.(.*?)\]/g;
|
||||
const restPropsRE = /\[\.\.\.(.*?)\]/;
|
||||
const deepMatchRE = /\[\.\.\..*?_deep\]/;
|
||||
const layoutNameRE = /@.+/g;
|
||||
const defaultIncludeRE = /\.md($|\?)/;
|
||||
|
||||
export type NoValue = null | undefined | void;
|
||||
|
||||
export type FalsyValue = false | NoValue;
|
||||
|
||||
export type HandleMetaRequestOptions = {
|
||||
extensions?: string[];
|
||||
filter?: (file: string) => boolean;
|
||||
resolve?: FileResolver | null | (FileResolver | FalsyValue)[];
|
||||
transform?: MetaTransform | null | (MetaTransform | FalsyValue)[];
|
||||
};
|
||||
|
||||
export type FileResolver = (
|
||||
slug: string,
|
||||
helpers: { resolve: typeof resolveSlug },
|
||||
) => ResolvedFile | FalsyValue | Promise<ResolvedFile | FalsyValue>;
|
||||
|
||||
export type ResolvedFile =
|
||||
| string
|
||||
| { file: string; transform: MetaTransform | (MetaTransform | FalsyValue)[] };
|
||||
|
||||
export type MetaTransform = (
|
||||
data: { slug: string; filePath: string; parser: MarkdownParser } & ParsedMarkdownResult,
|
||||
) => void | Promise<void>;
|
||||
|
||||
/**
|
||||
* Careful this function will throw if it can't match the `slug` param to a file.
|
||||
*/
|
||||
export async function handleMetaRequest(slugParam: string, options: HandleMetaRequestOptions = {}) {
|
||||
const { filter, extensions, resolve, transform } = options;
|
||||
|
||||
const slug = paramToSlug(slugParam);
|
||||
|
||||
const resolverArgs: Parameters<FileResolver> = [slug, { resolve: resolveSlug }];
|
||||
|
||||
let resolution: ResolvedFile | FalsyValue = null;
|
||||
|
||||
if (Array.isArray(resolve)) {
|
||||
for (const resolver of resolve) {
|
||||
if (resolver) resolution = await resolver?.(...resolverArgs);
|
||||
if (resolution) break;
|
||||
}
|
||||
} else {
|
||||
resolution = await resolve?.(...resolverArgs);
|
||||
}
|
||||
|
||||
if (!resolution) {
|
||||
resolution = resolveSlug(slug, { extensions });
|
||||
}
|
||||
|
||||
const resolvedFile = isString(resolution) ? resolution : resolution?.file;
|
||||
const resolvedTransform = isString(resolution) ? null : resolution?.transform;
|
||||
if (!resolvedFile) {
|
||||
throw Error('Could not find file.');
|
||||
}
|
||||
|
||||
if (filter && !filter(`/${cleanFilePath(resolvedFile)}`)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const filePath = path.isAbsolute(resolvedFile) ? resolvedFile : path.resolve(CWD, resolvedFile);
|
||||
const content = readFileSync(filePath).toString();
|
||||
if (!parser) {
|
||||
parser = await createMarkdownParser();
|
||||
}
|
||||
|
||||
let result = parseMarkdown(parser, content, filePath);
|
||||
result = JSON.parse(JSON.stringify(result));
|
||||
|
||||
const transformerArgs: Parameters<MetaTransform> = [{ slug, filePath, parser, ...result }];
|
||||
|
||||
const runTransform = async (transform?: HandleMetaRequestOptions['transform']) => {
|
||||
if (Array.isArray(transform)) {
|
||||
for (const transformer of transform) {
|
||||
if (transformer) await transformer?.(...transformerArgs);
|
||||
}
|
||||
} else {
|
||||
await transform?.(...transformerArgs);
|
||||
}
|
||||
};
|
||||
|
||||
await runTransform(transform);
|
||||
await runTransform(resolvedTransform);
|
||||
return result;
|
||||
}
|
||||
|
||||
export type CreateMetaRequestHandlerOptions = {
|
||||
include?: FilterPattern;
|
||||
exclude?: FilterPattern;
|
||||
debug?: boolean;
|
||||
} & HandleMetaRequestOptions;
|
||||
|
||||
export function createMetaRequestHandler(
|
||||
options: CreateMetaRequestHandlerOptions = {},
|
||||
): RequestHandler {
|
||||
const { include, exclude, debug, ...handlerOptions } = options;
|
||||
|
||||
const filter = createFilter(
|
||||
include ?? handlerOptions.extensions?.map((ext) => new RegExp(`${ext}$`)) ?? defaultIncludeRE,
|
||||
exclude,
|
||||
);
|
||||
|
||||
return async ({ params }) => {
|
||||
try {
|
||||
const res = await handleMetaRequest(params.slug as string, { filter, ...handlerOptions });
|
||||
if (!res) return new Response(null);
|
||||
return json(res.meta);
|
||||
} catch (e) {
|
||||
if (debug) {
|
||||
console.log(kleur.bold(kleur.red(`\n[kit-docs]: failed to handle meta request.`)));
|
||||
console.log(`\n\n${e}\n`);
|
||||
}
|
||||
}
|
||||
|
||||
return new Response(null);
|
||||
};
|
||||
}
|
||||
|
||||
const headingRE = /#\s(.*?)($|\n|\r)/;
|
||||
|
||||
export type HandleSidebarRequestOptions = {
|
||||
extensions?: string[];
|
||||
filter?: (file: string) => boolean;
|
||||
resolveTitle?: SidebarMetaResolver;
|
||||
resolveCategory?: SidebarMetaResolver;
|
||||
resolveSlug?: SidebarMetaResolver;
|
||||
formatCategoryName?: (name: string, helpers: { format: (name: string) => string }) => string;
|
||||
};
|
||||
|
||||
export type SidebarMetaResolver = (data: {
|
||||
filePath: string;
|
||||
relativeFilePath: string;
|
||||
cleanFilePath: string;
|
||||
dirname: string;
|
||||
cleanDirname: string;
|
||||
frontmatter: Record<string, any>;
|
||||
fileContent: string;
|
||||
resolve: () => string;
|
||||
slugify: typeof slugifyFilePath;
|
||||
}) => string | void | null | undefined | Promise<string | void | null | undefined>;
|
||||
|
||||
/**
|
||||
* Careful this function will throw if it can't match the `dir` param to a directory.
|
||||
*/
|
||||
export async function handleSidebarRequest(
|
||||
dirParam: string,
|
||||
options: HandleSidebarRequestOptions = {},
|
||||
) {
|
||||
const { extensions, filter, formatCategoryName, resolveTitle, resolveCategory, resolveSlug } =
|
||||
options;
|
||||
|
||||
const exts = extensions ?? ['.md'];
|
||||
const globExt =
|
||||
exts.length > 1 ? `.{${exts.map((ext) => ext.replace(/^\./, '')).join(',')}}` : exts[0];
|
||||
|
||||
const directory = paramToDir(dirParam);
|
||||
const dirPath = path.resolve(ROUTES_DIR, directory);
|
||||
|
||||
const filePaths = sortOrderedFiles(readDirDeepSync(dirPath));
|
||||
|
||||
const links: Record<string, { title: string; slug: string; match?: 'deep' }[]> = {};
|
||||
|
||||
// Root at top.
|
||||
links['.'] = [];
|
||||
let hasRoot = false;
|
||||
|
||||
for (const filePath of filePaths) {
|
||||
const filename = path.basename(filePath);
|
||||
const relativeFilePath = path.relative(ROUTES_DIR, filePath);
|
||||
const dirs = path.dirname(relativeFilePath).split('/');
|
||||
const cleanPath = cleanFilePath(filePath);
|
||||
const cleanDirs = path.dirname(cleanPath).split('/').slice(0, -1);
|
||||
const cleanDirsReversed = cleanDirs.slice().reverse();
|
||||
const isIndexFile = /\/\+page\./.test(cleanPath);
|
||||
const isShallowRoot = cleanDirs.length === 0;
|
||||
const isRoot = isShallowRoot || deepMatchRE.test(dirs[1]);
|
||||
let isDeepMatch = false;
|
||||
let isValidDeepMatch = false;
|
||||
|
||||
if (deepMatchRE.test(relativeFilePath)) {
|
||||
const deepMatchDir = dirs.findIndex((dir) => deepMatchRE.test(dir));
|
||||
isDeepMatch = deepMatchDir >= 0;
|
||||
|
||||
const glob = (depth: number) =>
|
||||
`src/routes/*${cleanDirs.slice(0, depth).join('/*')}/*+page*${globExt}`;
|
||||
|
||||
let file = isDeepMatch ? globbySync(glob(deepMatchDir + 1))?.[0] : null;
|
||||
|
||||
if (isDeepMatch && !file) {
|
||||
file = isDeepMatch ? globbySync(glob(deepMatchDir + 2))?.[0] : null;
|
||||
}
|
||||
|
||||
isValidDeepMatch = isDeepMatch ? file === `src/routes/${relativeFilePath}` : false;
|
||||
}
|
||||
|
||||
if (
|
||||
filename.startsWith('_') ||
|
||||
filename.startsWith('.') ||
|
||||
(isShallowRoot && isIndexFile) ||
|
||||
(isDeepMatch && !isValidDeepMatch) ||
|
||||
!(filter?.(`/${cleanPath}`) ?? true)
|
||||
) {
|
||||
continue;
|
||||
}
|
||||
|
||||
const fileContent = readFileSync(filePath).toString();
|
||||
const frontmatter = getFrontmatter(fileContent);
|
||||
|
||||
const resolverData = {
|
||||
filePath,
|
||||
relativeFilePath,
|
||||
cleanFilePath: cleanPath,
|
||||
frontmatter,
|
||||
fileContent,
|
||||
dirname: path.dirname(filePath),
|
||||
cleanDirname: path.dirname(cleanPath),
|
||||
slugify: slugifyFilePath,
|
||||
};
|
||||
|
||||
const categoryFormatter = formatCategoryName ?? kebabToTitleCase;
|
||||
|
||||
const formatCategory = (dirname: string) =>
|
||||
categoryFormatter(dirname, { format: (name) => kebabToTitleCase(name) });
|
||||
|
||||
const resolveDefaultTitle = () =>
|
||||
frontmatter.sidebar_title ??
|
||||
frontmatter.title ??
|
||||
(isDeepMatch ? formatCategory(cleanDirsReversed[0]) : null) ??
|
||||
fileContent.match(headingRE)?.[1] ??
|
||||
kebabToTitleCase(path.basename(cleanPath, path.extname(cleanPath)));
|
||||
|
||||
const resolveDefaultCategory = () =>
|
||||
isRoot ? '.' : cleanDirsReversed[isIndexFile && isDeepMatch ? 1 : 0];
|
||||
|
||||
const resolveDefaultSlug = () => slugifyFilePath(filePath);
|
||||
|
||||
const category = formatCategory(
|
||||
(await resolveCategory?.({ ...resolverData, resolve: resolveDefaultCategory })) ??
|
||||
resolveDefaultCategory(),
|
||||
);
|
||||
|
||||
const title =
|
||||
(await resolveTitle?.({ ...resolverData, resolve: resolveDefaultTitle })) ??
|
||||
resolveDefaultTitle();
|
||||
|
||||
const slug =
|
||||
(await resolveSlug?.({ ...resolverData, resolve: resolveDefaultSlug })) ??
|
||||
resolveDefaultSlug();
|
||||
|
||||
const match = isDeepMatch ? 'deep' : undefined;
|
||||
|
||||
(links[category] ??= []).push({ title, slug, match });
|
||||
if (!hasRoot) hasRoot = category === '.';
|
||||
}
|
||||
|
||||
if (!hasRoot) {
|
||||
delete links['.'];
|
||||
}
|
||||
|
||||
return { links };
|
||||
}
|
||||
|
||||
export type CreateSidebarRequestHandlerOptions = {
|
||||
include?: FilterPattern;
|
||||
exclude?: FilterPattern;
|
||||
debug?: boolean;
|
||||
} & HandleSidebarRequestOptions;
|
||||
|
||||
export function createSidebarRequestHandler(
|
||||
options: CreateSidebarRequestHandlerOptions = {},
|
||||
): RequestHandler {
|
||||
const { include, debug, exclude, ...handlerOptions } = options;
|
||||
|
||||
const filter = createFilter(
|
||||
include ?? handlerOptions.extensions?.map((ext) => new RegExp(`${ext}$`)) ?? defaultIncludeRE,
|
||||
exclude,
|
||||
);
|
||||
|
||||
return async ({ params }) => {
|
||||
try {
|
||||
const { links } = await handleSidebarRequest(params.dir as string, {
|
||||
filter,
|
||||
...handlerOptions,
|
||||
});
|
||||
|
||||
return json({ links });
|
||||
} catch (e) {
|
||||
if (debug) {
|
||||
console.log(kleur.bold(kleur.red(`\n[kit-docs]: failed to handle sidebar request.`)));
|
||||
console.log(`\n\n${e}\n`);
|
||||
}
|
||||
}
|
||||
|
||||
return new Response(null);
|
||||
};
|
||||
}
|
||||
|
||||
export type ResolveSlugOptions = {
|
||||
extensions?: string[];
|
||||
};
|
||||
|
||||
/**
|
||||
* Attempts to resolve the given slug to a file in the `routes` directory. This function returns
|
||||
* a relative file path.
|
||||
*/
|
||||
export function resolveSlug(slug: string, options: ResolveSlugOptions = {}): string | null {
|
||||
const { extensions } = options;
|
||||
|
||||
const exts = extensions ?? ['.md'];
|
||||
|
||||
const globExt =
|
||||
exts.length > 1 ? `.{${exts.map((ext) => ext.replace(/^\./, '')).join(',')}}` : exts[0];
|
||||
|
||||
const fileGlobBase = `src/routes/${slug
|
||||
.split('/')
|
||||
.slice(0, -1)
|
||||
.map((s) => `*${s}`)
|
||||
.join('/')}`;
|
||||
|
||||
const glob = `${fileGlobBase}/*${path.basename(slug)}/*${globExt}`;
|
||||
let file = globbySync(glob)?.[0];
|
||||
|
||||
if (!file) {
|
||||
const glob = `${fileGlobBase}/*${path.basename(slug)}/*index*${globExt}`;
|
||||
file = globbySync(glob)?.[0];
|
||||
}
|
||||
|
||||
if (!file) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const matchedSlug = file
|
||||
.replace(restParamsRE, '')
|
||||
.replace(layoutNameRE, '')
|
||||
.replace(path.extname(file), '')
|
||||
.replace(/\/index$/, slug === 'index' ? '/index' : '');
|
||||
|
||||
if (matchedSlug !== `src/routes/${slug}/+page` || !exts.some((ext) => file.endsWith(ext))) {
|
||||
return null;
|
||||
}
|
||||
return file;
|
||||
}
|
||||
|
||||
/**
|
||||
* Takes an absolute or relative file path and maps it to a relative path to `src/routes`, and
|
||||
* strips out rest params and layout ids `{[...1]}index{@layout-id}.md`.
|
||||
*
|
||||
* @example `src/routes/docs/[...1getting-started]/[...1]intro.md` = `docs/getting-started/intro.md`
|
||||
*/
|
||||
export function cleanFilePath(filePath: string) {
|
||||
const relativePath = path.relative(ROUTES_DIR, filePath);
|
||||
return relativePath.replace(restParamsRE, '').replace(layoutNameRE, path.extname(filePath));
|
||||
}
|
||||
|
||||
export function paramToSlug(param: string) {
|
||||
return param.replace(/_/g, '/').replace(/\.html/, '');
|
||||
}
|
||||
|
||||
export function paramToDir(param: string) {
|
||||
return paramToSlug(param);
|
||||
}
|
||||
|
||||
/**
|
||||
* Maps a path that points to a file in the `routes` directory to a slug. The file path
|
||||
* can be absolute or relative to the `routes` directory.
|
||||
*/
|
||||
export function slugifyFilePath(filePath: string) {
|
||||
const cleanPath = cleanFilePath(filePath);
|
||||
return `/${cleanPath
|
||||
.replace(path.extname(cleanPath), '')
|
||||
.replace(/\/?index$/, '')
|
||||
.replace(/\/\+page$/, '')}`;
|
||||
}
|
@ -1,51 +0,0 @@
|
||||
import path from 'path';
|
||||
import {
|
||||
type Highlighter,
|
||||
type HighlighterOptions,
|
||||
type Lang,
|
||||
getHighlighter,
|
||||
renderToHtml,
|
||||
} from 'shiki';
|
||||
import { type Plugin } from 'vite';
|
||||
|
||||
const PLUGIN_NAME = '@svelteness/highlight' as const;
|
||||
|
||||
export type HighlightPluginOptions = HighlighterOptions;
|
||||
|
||||
export const kitDocsHighlightPlugin = (options: HighlightPluginOptions = {}): Plugin => {
|
||||
let highlighter: Highlighter;
|
||||
|
||||
const highlightQueryRE = /\?highlight/;
|
||||
|
||||
return {
|
||||
name: PLUGIN_NAME,
|
||||
enforce: 'pre' as const,
|
||||
async configResolved() {
|
||||
highlighter = await getHighlighter({
|
||||
theme: 'material-palenight',
|
||||
langs: [],
|
||||
...options,
|
||||
});
|
||||
},
|
||||
transform(code, id) {
|
||||
if (!highlightQueryRE.test(id)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const lang = (new URLSearchParams(id).get('lang') ??
|
||||
path.extname(id.replace(highlightQueryRE, '')).slice(1)) as Lang;
|
||||
|
||||
const tokens = highlighter.codeToThemedTokens(code, lang);
|
||||
|
||||
const html = renderToHtml(tokens)
|
||||
.replace(/\sclass="shiki" style=".*?"/, '')
|
||||
.trim();
|
||||
|
||||
return `
|
||||
export const tokens = ${JSON.stringify(tokens)}
|
||||
export const code = ${JSON.stringify(code)}
|
||||
export const hlCode = ${JSON.stringify(html)}
|
||||
`;
|
||||
},
|
||||
};
|
||||
};
|
@ -1,7 +0,0 @@
|
||||
export * from './handlers';
|
||||
export * from './highlight-plugin';
|
||||
export * from './kit-docs-plugin';
|
||||
export { kitDocsPlugin as default } from './kit-docs-plugin';
|
||||
export * from './markdown-plugin';
|
||||
export * from './markdown-plugin/parser';
|
||||
export { kebabToTitleCase } from './utils/string';
|
@ -1,64 +0,0 @@
|
||||
import { resolve } from 'path';
|
||||
import { type HighlighterOptions } from 'shiki';
|
||||
import { type Plugin } from 'vite';
|
||||
|
||||
import { kitDocsHighlightPlugin } from './highlight-plugin';
|
||||
import { type MarkdownPluginOptions, kitDocsMarkdownPlugin } from './markdown-plugin';
|
||||
|
||||
const __cwd = process.cwd();
|
||||
|
||||
export type KitDocsPluginOptions = {
|
||||
highlight?: false;
|
||||
shiki?: HighlighterOptions;
|
||||
markdown?: MarkdownPluginOptions;
|
||||
};
|
||||
|
||||
export const kitDocsPlugin = (options: KitDocsPluginOptions = {}): Plugin[] =>
|
||||
[
|
||||
corePlugin(),
|
||||
options.highlight !== false && kitDocsHighlightPlugin(options.shiki),
|
||||
kitDocsMarkdownPlugin({ ...options.markdown, shiki: options.shiki }),
|
||||
].filter(Boolean) as Plugin[];
|
||||
|
||||
function corePlugin(): Plugin {
|
||||
return {
|
||||
name: '@svelteness/kit-docs',
|
||||
enforce: 'pre',
|
||||
config(config) {
|
||||
const userAlias = config.resolve?.alias;
|
||||
|
||||
const aliasKeys: string[] = !Array.isArray(userAlias)
|
||||
? Object.keys(userAlias ?? {})
|
||||
: userAlias.map((alias) => alias.find) ?? [];
|
||||
|
||||
const hasAlias = (alias: string) => aliasKeys.includes(alias);
|
||||
|
||||
const alias = {
|
||||
$fonts: resolve(__cwd, 'src/fonts'),
|
||||
$img: resolve(__cwd, 'src/img'),
|
||||
$kitDocs: resolve(__cwd, 'src/kit-docs'),
|
||||
};
|
||||
|
||||
for (const find of Object.keys(alias)) {
|
||||
if (hasAlias(find)) {
|
||||
delete alias[find];
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
optimizeDeps: {
|
||||
include: ['shiki'],
|
||||
exclude: ['@svelteness/kit-docs'],
|
||||
},
|
||||
resolve: {
|
||||
alias,
|
||||
},
|
||||
build: {
|
||||
rollupOptions: {
|
||||
external: ['@svelteness/kit-docs/node'],
|
||||
},
|
||||
},
|
||||
};
|
||||
},
|
||||
};
|
||||
}
|
@ -1,192 +0,0 @@
|
||||
import { type FilterPattern, createFilter, normalizePath } from '@rollup/pluginutils';
|
||||
import { globbySync } from 'globby';
|
||||
import { resolve } from 'path';
|
||||
import { fileURLToPath } from 'url';
|
||||
import { type Plugin } from 'vite';
|
||||
|
||||
import { isLocalEnv } from '../utils/env';
|
||||
import { getFileNameFromPath } from '../utils/path';
|
||||
import {
|
||||
type MarkdownComponents,
|
||||
type MarkdownParser,
|
||||
type MarkdownParserOptions,
|
||||
type ParseMarkdownOptions,
|
||||
AddTopLevelHtmlTags,
|
||||
clearMarkdownCaches,
|
||||
createMarkdownParser,
|
||||
MarkdownComponentContainer,
|
||||
parseMarkdownToSvelte,
|
||||
} from './parser';
|
||||
|
||||
const PLUGIN_NAME = '@svelteness/markdown' as const;
|
||||
|
||||
const __cwd = process.cwd();
|
||||
// @ts-ignore
|
||||
const __dirname = fileURLToPath(import.meta.url);
|
||||
|
||||
export type MarkdownPluginOptions = MarkdownParserOptions & {
|
||||
/**
|
||||
* The markdown files to be parsed and rendered as Svelte components.
|
||||
*
|
||||
* @defaultValue /\+page\.md($|\?)/
|
||||
*/
|
||||
include?: FilterPattern;
|
||||
/**
|
||||
* The markdown files to _not_ be parsed.
|
||||
*
|
||||
* @defaultValue `null`
|
||||
*/
|
||||
exclude?: FilterPattern;
|
||||
/**
|
||||
* A glob pointing to Svelte component files that will be imported into every single
|
||||
* markdown file.
|
||||
*
|
||||
* @defaultValue 'src/kit-docs/**\/[^_]*.svelte'
|
||||
*/
|
||||
globalComponents?: string;
|
||||
/**
|
||||
* Add custom top-level tags (e.g., `<svelte:head>`, `<script>` or `<style>`) to a markdown
|
||||
* Svelte component.
|
||||
*
|
||||
* @defaultValue `null`
|
||||
*/
|
||||
topLevelHtmlTags?: AddTopLevelHtmlTags;
|
||||
};
|
||||
|
||||
const DEFAULT_INCLUDE_RE = /\+page\.md($|\?)/;
|
||||
const DEFAULT_EXCLUDE_RE = null;
|
||||
const DEFAULT_GLOBAL_COMPONENTS = 'src/kit-docs/**/[^_]*.svelte';
|
||||
|
||||
export function kitDocsMarkdownPlugin(options: MarkdownPluginOptions = {}): Plugin {
|
||||
let mode: string;
|
||||
let baseUrl: string;
|
||||
let parser: MarkdownParser;
|
||||
let isBuild: boolean;
|
||||
let define: Record<string, unknown> | undefined;
|
||||
|
||||
const {
|
||||
include = DEFAULT_INCLUDE_RE,
|
||||
exclude = DEFAULT_EXCLUDE_RE,
|
||||
globalComponents = DEFAULT_GLOBAL_COMPONENTS,
|
||||
topLevelHtmlTags,
|
||||
...parserOptions
|
||||
} = options;
|
||||
|
||||
const filter = createFilter(
|
||||
options.include ?? DEFAULT_INCLUDE_RE,
|
||||
options.exclude ?? DEFAULT_EXCLUDE_RE,
|
||||
);
|
||||
|
||||
/** Page system file paths. */
|
||||
const files = new Set<string>();
|
||||
|
||||
const globalComponentFiles = globbySync(globalComponents).map(normalizePath);
|
||||
|
||||
const parseOptions = (): ParseMarkdownOptions => ({
|
||||
mode,
|
||||
baseUrl,
|
||||
escapeConstants: isBuild,
|
||||
define,
|
||||
globalComponentFiles,
|
||||
topLevelHtmlTags,
|
||||
});
|
||||
|
||||
const components: MarkdownComponents = parserOptions?.components ?? [];
|
||||
|
||||
function addGlobalComponents(files: string[]) {
|
||||
for (const file of files) {
|
||||
const name = getFileNameFromPath(file);
|
||||
const has = globalComponentFiles.some((file) => getFileNameFromPath(file) === name);
|
||||
if (!has) globalComponentFiles.push(file);
|
||||
}
|
||||
}
|
||||
|
||||
function addMarkdownComponents(files: string[]) {
|
||||
for (const file of files) {
|
||||
const componentName = getFileNameFromPath(file);
|
||||
const has = components.some(({ name, type }) => type === 'custom' && name === componentName);
|
||||
if (!has) {
|
||||
components.push({
|
||||
name: componentName,
|
||||
type: 'custom',
|
||||
container: getMarkdownContainer(file, componentName),
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const absGlobalComponentPaths = globalComponentFiles
|
||||
.map((path) => resolve(__cwd, path))
|
||||
.map(normalizePath);
|
||||
addMarkdownComponents(absGlobalComponentPaths);
|
||||
|
||||
try {
|
||||
const root = isLocalEnv()
|
||||
? resolve(__cwd, 'src/lib/kit-docs')
|
||||
: resolve(__dirname, '../../client/kit-docs');
|
||||
|
||||
const paths = globbySync('**/*.svelte', { cwd: root }).map(normalizePath);
|
||||
const absPaths = paths.map((path) => resolve(root, path)).map(normalizePath);
|
||||
|
||||
addMarkdownComponents(absPaths);
|
||||
addGlobalComponents(absPaths);
|
||||
} catch (e) {
|
||||
// no-op
|
||||
}
|
||||
|
||||
return {
|
||||
name: PLUGIN_NAME,
|
||||
enforce: 'pre' as const,
|
||||
async configResolved(config) {
|
||||
baseUrl = config.base;
|
||||
mode = config.mode;
|
||||
isBuild = config.command === 'build';
|
||||
define = config.define;
|
||||
parser = await createMarkdownParser({
|
||||
...parserOptions,
|
||||
components,
|
||||
});
|
||||
},
|
||||
configureServer(server) {
|
||||
function restart() {
|
||||
clearMarkdownCaches();
|
||||
files.clear();
|
||||
server.restart();
|
||||
}
|
||||
|
||||
server.watcher
|
||||
.add(globalComponents)
|
||||
.on('add', () => restart())
|
||||
.on('unlink', () => restart());
|
||||
},
|
||||
transform(code, id) {
|
||||
if (filter(id)) {
|
||||
const filePath = normalizePath(id);
|
||||
|
||||
const { component } = parseMarkdownToSvelte(parser, code, filePath, parseOptions());
|
||||
files.add(filePath);
|
||||
return component;
|
||||
}
|
||||
|
||||
return null;
|
||||
},
|
||||
async handleHotUpdate(ctx) {
|
||||
const { file, read } = ctx;
|
||||
|
||||
// Hot reload `.md` files as `.svelte` files.
|
||||
if (files.has(file)) {
|
||||
const content = await read();
|
||||
const { component } = parseMarkdownToSvelte(parser, content, file, parseOptions());
|
||||
ctx.read = () => component;
|
||||
}
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
function getMarkdownContainer(path: string, name: string): MarkdownComponentContainer | undefined {
|
||||
if (!path.includes('kit-docs')) return;
|
||||
|
||||
if (name === 'Step') return { marker: '!' };
|
||||
|
||||
return undefined;
|
||||
}
|
@ -1,119 +0,0 @@
|
||||
import MarkdownIt from 'markdown-it';
|
||||
import { type HighlighterOptions } from 'shiki';
|
||||
|
||||
import {
|
||||
anchorPlugin,
|
||||
codePlugin,
|
||||
containersPlugin,
|
||||
createShikiPlugin,
|
||||
customComponentPlugin,
|
||||
emojiPlugin,
|
||||
extractHeadersPlugin,
|
||||
extractTitlePlugin,
|
||||
hoistTagsPlugin,
|
||||
importCodePlugin,
|
||||
linksPlugin,
|
||||
tocPlugin,
|
||||
} from './plugins';
|
||||
import type {
|
||||
InlineElementRule,
|
||||
MarkdownBlockComponent,
|
||||
MarkdownComponents,
|
||||
MarkdownCustomComponent,
|
||||
MarkdownInlineComponent,
|
||||
MarkdownParser,
|
||||
} from './types';
|
||||
|
||||
export type MarkdownParserOptions = {
|
||||
components?: MarkdownComponents;
|
||||
shiki?: HighlighterOptions;
|
||||
configureParser?(parser: MarkdownParser): void | Promise<void>;
|
||||
};
|
||||
|
||||
export async function createMarkdownParser(
|
||||
options: MarkdownParserOptions = {},
|
||||
): Promise<MarkdownParser> {
|
||||
const { configureParser, shiki = {}, components = [] } = options;
|
||||
|
||||
const inlineComponents = components.filter(
|
||||
({ type }) => type === 'inline',
|
||||
) as MarkdownInlineComponent[];
|
||||
|
||||
const blockComponents = components.filter(
|
||||
({ type }) => type === 'block',
|
||||
) as MarkdownBlockComponent[];
|
||||
|
||||
const customComponents = components.filter(
|
||||
({ type }) => type === 'custom',
|
||||
) as MarkdownCustomComponent[];
|
||||
|
||||
const parser = MarkdownIt({ html: true });
|
||||
|
||||
parser.use(emojiPlugin);
|
||||
parser.use(anchorPlugin);
|
||||
parser.use(tocPlugin);
|
||||
parser.use(extractHeadersPlugin);
|
||||
parser.use(extractTitlePlugin);
|
||||
parser.use(customComponentPlugin);
|
||||
parser.use(linksPlugin);
|
||||
parser.use(codePlugin);
|
||||
parser.use(containersPlugin, customComponents);
|
||||
parser.use(importCodePlugin);
|
||||
parser.use(await createShikiPlugin(shiki));
|
||||
parser.use(hoistTagsPlugin);
|
||||
|
||||
responsiveTablePlugin(parser);
|
||||
|
||||
const inlineRuleMap: Partial<Record<InlineElementRule, string>> = {
|
||||
strikethrough: 's',
|
||||
emphasized: 'em',
|
||||
};
|
||||
|
||||
for (const { name, rule } of inlineComponents) {
|
||||
if (rule === 'image') {
|
||||
parser.renderer.rules.image = function (tokens, idx, _, __, self) {
|
||||
const token = tokens[idx];
|
||||
return `<${name} ${self.renderAttrs(token)} />`;
|
||||
};
|
||||
continue;
|
||||
}
|
||||
|
||||
const mappedRule = inlineRuleMap[rule] ?? rule;
|
||||
parser.renderer.rules[`${mappedRule}_open`] = () => {
|
||||
return `<${name}>`;
|
||||
};
|
||||
parser.renderer.rules[`${mappedRule}_close`] = () => {
|
||||
return `</${name}>`;
|
||||
};
|
||||
}
|
||||
|
||||
for (const { name, rule } of blockComponents) {
|
||||
parser.renderer.rules[`${rule}_open`] = (tokens, idx) => {
|
||||
const token = tokens[idx];
|
||||
const props: string[] = [];
|
||||
|
||||
if (/h(\d)/.test(token.tag)) {
|
||||
props.push(`level=${token.tag.slice(1)}`);
|
||||
}
|
||||
|
||||
return `<${name} ${props.join(' ')}>`;
|
||||
};
|
||||
parser.renderer.rules[`${rule}_close`] = () => {
|
||||
return `</${name}>`;
|
||||
};
|
||||
}
|
||||
|
||||
await configureParser?.(parser);
|
||||
|
||||
return parser;
|
||||
}
|
||||
|
||||
function responsiveTablePlugin(parser: MarkdownParser) {
|
||||
parser.renderer.rules.table_open = function () {
|
||||
return `<TableWrapper><table>`;
|
||||
};
|
||||
|
||||
parser.renderer.rules.table_close = function () {
|
||||
return '</table></TableWrapper>';
|
||||
};
|
||||
}
|
@ -1,4 +0,0 @@
|
||||
export * from './createMarkdownParser';
|
||||
export * from './parseMarkdown';
|
||||
export * from './plugins';
|
||||
export * from './types';
|
@ -1,205 +0,0 @@
|
||||
import fs from 'fs';
|
||||
import matter from 'gray-matter';
|
||||
import LRUCache from 'lru-cache';
|
||||
import toml from 'toml';
|
||||
|
||||
import { isLocalEnv } from '../../utils/env';
|
||||
import { getFileNameFromPath } from '../../utils/path';
|
||||
import { hashString } from '../../utils/string';
|
||||
import type {
|
||||
MarkdownMeta,
|
||||
MarkdownParser,
|
||||
MarkdownParserEnv,
|
||||
ParsedMarkdownResult,
|
||||
ParseMarkdownOptions,
|
||||
} from './types';
|
||||
import { commentOutTemplateTags, uncommentTemplateTags } from './utils/htmlEscape';
|
||||
import { preventViteReplace } from './utils/preventViteReplace';
|
||||
|
||||
const kitDocsImportPath = isLocalEnv() ? '$lib' : '@svelteness/kit-docs';
|
||||
|
||||
export type ParseMarkdownToSvelteResult = {
|
||||
component: string;
|
||||
meta: MarkdownMeta;
|
||||
};
|
||||
|
||||
const svelteCache = new LRUCache<string, ParseMarkdownToSvelteResult>({ max: 1024 });
|
||||
export function parseMarkdownToSvelte(
|
||||
parser: MarkdownParser,
|
||||
source: string,
|
||||
filePath: string,
|
||||
options: ParseMarkdownOptions = {},
|
||||
): ParseMarkdownToSvelteResult {
|
||||
const isProd = options.mode === 'production';
|
||||
const cacheKey = !isProd ? hashString(filePath + source) : '';
|
||||
|
||||
if (!isProd && svelteCache.has(cacheKey)) return svelteCache.get(cacheKey)!;
|
||||
|
||||
const {
|
||||
html,
|
||||
meta,
|
||||
env: parserEnv,
|
||||
} = parseMarkdown(parser, commentOutTemplateTags(source), filePath, {
|
||||
...options,
|
||||
});
|
||||
|
||||
const { hoistedTags = [] } = parserEnv as MarkdownParserEnv;
|
||||
|
||||
const fileName = getFileNameFromPath(filePath);
|
||||
|
||||
if (kitDocsImportPath.length) {
|
||||
hoistedTags.push(
|
||||
['<script>', `import { frontmatter } from "${kitDocsImportPath}";`, '</script>'].join('\n'),
|
||||
);
|
||||
}
|
||||
|
||||
hoistedTags.push(...(options.topLevelHtmlTags?.({ fileName, filePath, meta }) ?? []));
|
||||
|
||||
if (options.globalComponentFiles) {
|
||||
addGlobalImports(hoistedTags, options.globalComponentFiles);
|
||||
}
|
||||
|
||||
const component =
|
||||
dedupeHoistedTags(hoistedTags).join('\n') + `\n\n${uncommentTemplateTags(html)}`;
|
||||
|
||||
const result: ParseMarkdownToSvelteResult = {
|
||||
component,
|
||||
meta,
|
||||
};
|
||||
|
||||
svelteCache.set(cacheKey, result);
|
||||
return result;
|
||||
}
|
||||
|
||||
function addGlobalImports(tags: string[], files: string[]) {
|
||||
const globalImports = files
|
||||
.map((filePath) => {
|
||||
const componentName = getFileNameFromPath(filePath);
|
||||
return `import ${componentName} from '/${filePath.replace(/^\//, '')}';`;
|
||||
})
|
||||
.join('\n');
|
||||
|
||||
tags.push(['<script>', globalImports, '</script>'].join('\n'));
|
||||
}
|
||||
|
||||
const frontmatterCache = new LRUCache({ max: 1024 });
|
||||
export function getFrontmatter(source: string): Record<string, any> {
|
||||
const cacheKey = hashString(source);
|
||||
|
||||
if (frontmatterCache.has(cacheKey)) return frontmatterCache.get(cacheKey)!;
|
||||
|
||||
const { data: frontmatter } = matter(source, {
|
||||
excerpt_separator: '<!-- more -->',
|
||||
engines: {
|
||||
toml: toml.parse.bind(toml),
|
||||
},
|
||||
});
|
||||
|
||||
frontmatterCache.set(cacheKey, frontmatter ?? {});
|
||||
return frontmatter ?? {};
|
||||
}
|
||||
|
||||
const mdCache = new LRUCache<string, ParsedMarkdownResult>({ max: 1024 });
|
||||
export function parseMarkdown(
|
||||
parser: MarkdownParser,
|
||||
source: string,
|
||||
filePath: string,
|
||||
options: ParseMarkdownOptions = {},
|
||||
): ParsedMarkdownResult {
|
||||
const isProd = options.mode === 'production';
|
||||
const cacheKey = !isProd ? hashString(filePath + source) : '';
|
||||
|
||||
if (!isProd && mdCache.has(cacheKey)) return mdCache.get(cacheKey)!;
|
||||
|
||||
const {
|
||||
data: frontmatter,
|
||||
content,
|
||||
excerpt,
|
||||
} = matter(source, {
|
||||
excerpt_separator: '<!-- more -->',
|
||||
engines: {
|
||||
toml: toml.parse.bind(toml),
|
||||
},
|
||||
});
|
||||
|
||||
const parserEnv: MarkdownParserEnv = {
|
||||
filePath,
|
||||
frontmatter,
|
||||
};
|
||||
|
||||
let html = parser.render(content, parserEnv);
|
||||
|
||||
const excerptHtml = parser.render(excerpt ?? '');
|
||||
|
||||
if (options.escapeConstants) {
|
||||
html = preventViteReplace(html, options.define);
|
||||
}
|
||||
|
||||
const { headers = [], importedFiles = [], links = [], title = '' } = parserEnv;
|
||||
|
||||
const _title = frontmatter.title ?? title;
|
||||
const description = frontmatter.description;
|
||||
|
||||
const result: ParsedMarkdownResult = {
|
||||
content,
|
||||
html,
|
||||
links,
|
||||
importedFiles,
|
||||
env: parserEnv,
|
||||
meta: {
|
||||
excerpt: excerptHtml,
|
||||
headers,
|
||||
title: _title,
|
||||
description,
|
||||
frontmatter,
|
||||
lastUpdated: Math.round(fs.statSync(filePath).mtimeMs),
|
||||
},
|
||||
};
|
||||
|
||||
mdCache.set(cacheKey, result);
|
||||
return result;
|
||||
}
|
||||
|
||||
const OPENING_SCRIPT_TAG_RE = /<\s*script[^>]*>/;
|
||||
const OPENING_SCRIPT_MODULE_TAG_RE = /<\s*script[^>]*\scontext="module"\s*[^>]*>/;
|
||||
const CLOSING_SCRIPT_TAG_RE = /<\/script>/;
|
||||
const OPENING_STYLE_TAG_RE = /<\s*style[^>]*>/;
|
||||
const CLOSING_STYLE_TAG_RE = /<\/style>/;
|
||||
const OPENING_SVELTE_HEAD_TAG_RE = /<\s*svelte:head[^>]*>/;
|
||||
const CLOSING_SVELTE_HEAD_TAG_RE = /<\/svelte:head>/;
|
||||
function dedupeHoistedTags(tags: string[] = []): string[] {
|
||||
const dedupe = new Map();
|
||||
|
||||
const merge = (key: string, tag: string, openingTagRe: RegExp, closingTagRE: RegExp) => {
|
||||
if (!dedupe.has(key)) {
|
||||
dedupe.set(key, tag);
|
||||
return;
|
||||
}
|
||||
|
||||
const block = dedupe.get(key)!;
|
||||
dedupe.set(key, block.replace(closingTagRE, tag.replace(openingTagRe, '')));
|
||||
};
|
||||
|
||||
tags.forEach((tag) => {
|
||||
if (OPENING_SCRIPT_MODULE_TAG_RE.test(tag)) {
|
||||
merge('module', tag, OPENING_SCRIPT_MODULE_TAG_RE, CLOSING_SCRIPT_TAG_RE);
|
||||
} else if (OPENING_SCRIPT_TAG_RE.test(tag)) {
|
||||
merge('script', tag, OPENING_SCRIPT_TAG_RE, CLOSING_SCRIPT_TAG_RE);
|
||||
} else if (OPENING_STYLE_TAG_RE.test(tag)) {
|
||||
merge('style', tag, OPENING_STYLE_TAG_RE, CLOSING_STYLE_TAG_RE);
|
||||
} else if (OPENING_SVELTE_HEAD_TAG_RE.test(tag)) {
|
||||
merge('svelte:head', tag, OPENING_SVELTE_HEAD_TAG_RE, CLOSING_SVELTE_HEAD_TAG_RE);
|
||||
} else {
|
||||
// Treat unknowns as unique and leave them as-is.
|
||||
dedupe.set(Symbol(), tag);
|
||||
}
|
||||
});
|
||||
|
||||
return Array.from(dedupe.values());
|
||||
}
|
||||
|
||||
export function clearMarkdownCaches() {
|
||||
frontmatterCache.clear();
|
||||
mdCache.clear();
|
||||
svelteCache.clear();
|
||||
}
|
@ -1,18 +0,0 @@
|
||||
import type { PluginSimple } from 'markdown-it';
|
||||
import rawAnchorPlugin from 'markdown-it-anchor';
|
||||
|
||||
import { slugify } from '../utils/slugify';
|
||||
|
||||
export const anchorPlugin: PluginSimple = (parser) => {
|
||||
return rawAnchorPlugin(parser, {
|
||||
level: [2, 3, 4, 5, 6],
|
||||
slugify,
|
||||
permalink: rawAnchorPlugin.permalink.ariaHidden({
|
||||
class: 'header-anchor',
|
||||
symbol: '#',
|
||||
space: true,
|
||||
placement: 'before',
|
||||
// renderAttrs: () => ({ 'sveltekit:noscroll': '' })
|
||||
}),
|
||||
});
|
||||
};
|
@ -1,77 +0,0 @@
|
||||
import type { PluginSimple } from 'markdown-it';
|
||||
|
||||
import { uncommentTemplateTags } from '../../utils/htmlEscape';
|
||||
import { resolveHighlightLines } from './resolveHighlightLines';
|
||||
import { resolveLanguage } from './resolveLanguage';
|
||||
|
||||
/**
|
||||
* Plugin to enable styled code fences with line numbers, syntax highlighting, etc.
|
||||
*/
|
||||
export const codePlugin: PluginSimple = (parser) => {
|
||||
parser.renderer.rules.code_inline = (tokens, idx) => {
|
||||
const token = tokens[idx];
|
||||
const code = token.content;
|
||||
const props = [`code={${JSON.stringify(code)}}`].join(' ');
|
||||
return `<CodeInline ${props} />`;
|
||||
};
|
||||
|
||||
// Override default fence renderer.
|
||||
parser.renderer.rules.fence = (tokens, idx, options) => {
|
||||
const token = tokens[idx];
|
||||
|
||||
// Get token info.
|
||||
const info = token.info ? parser.utils.unescapeAll(token.info).trim() : '';
|
||||
|
||||
// Resolve language from token info.
|
||||
const language = resolveLanguage(info);
|
||||
|
||||
// Get un-escaped code content.
|
||||
const content = uncommentTemplateTags(token.content);
|
||||
|
||||
// Try to get highlighted code.
|
||||
const html =
|
||||
options.highlight?.(content, language.name, '') || parser.utils.escapeHtml(content);
|
||||
|
||||
const code = html.replace(/\sclass="shiki" style=".*?"/, '').trim();
|
||||
|
||||
const rawCode = token.content
|
||||
.replace(/<script/g, '<script​')
|
||||
.replace(/<style/g, '<style​');
|
||||
|
||||
const linesCount = (html.match(/"line"/g) || []).length;
|
||||
|
||||
// Resolve highlight line ranges from token info.
|
||||
const highlightLinesRanges = resolveHighlightLines(info);
|
||||
|
||||
const highlight = `[${highlightLinesRanges
|
||||
?.map((range) => `[${range[0]}, ${range[1]}]`)
|
||||
.join(',')}]`;
|
||||
|
||||
const title = info.match(/\|?title="?(.*?)"?(\||{|$)/)?.[1];
|
||||
const useLineNumbers = /\|?lineNumbers/.test(info);
|
||||
const showCopyCode = /\|?copy/.test(info);
|
||||
const copyHighlightOnly = /\|?copyHighlight/.test(info);
|
||||
const copySteps = /\|?copySteps/.test(info);
|
||||
const slot =
|
||||
info.match(/\|?slot="?(.*?)"?(\||{|$)/)?.[1] ?? (/\|?slot/.test(info) && language.ext);
|
||||
|
||||
const props = [
|
||||
title && `title="${title}"`,
|
||||
`lang="${language.name}"`,
|
||||
`ext="${language.ext}"`,
|
||||
`linesCount={${linesCount}}`,
|
||||
useLineNumbers && 'showLineNumbers',
|
||||
(highlightLinesRanges?.length ?? 0) > 0 && `highlightLines={${highlight}}`,
|
||||
showCopyCode && `rawCode={${JSON.stringify(rawCode)}}`,
|
||||
showCopyCode && 'showCopyCode',
|
||||
copyHighlightOnly && `copyHighlightOnly`,
|
||||
copySteps && 'copySteps',
|
||||
`code={${JSON.stringify(code)}}`,
|
||||
slot && `slot="${slot}"`,
|
||||
]
|
||||
.filter(Boolean)
|
||||
.join(' ');
|
||||
|
||||
return `<CodeFence ${props} />`;
|
||||
};
|
||||
};
|
@ -1,4 +0,0 @@
|
||||
export * from './codePlugin';
|
||||
export * from './languages';
|
||||
export * from './resolveHighlightLines';
|
||||
export * from './resolveLanguage';
|
@ -1,101 +0,0 @@
|
||||
/**
|
||||
* Language type for syntax highlight.
|
||||
*/
|
||||
export type HighlightLanguage = {
|
||||
/**
|
||||
* Name of the language.
|
||||
*
|
||||
* The name to be used for the class name, e.g. `class="language-typescript"`.
|
||||
*/
|
||||
name: string;
|
||||
|
||||
/**
|
||||
* Extension of the language.
|
||||
*
|
||||
* The file extension, which will be used for the class name, e.g. `class="ext-ts"`
|
||||
*/
|
||||
ext: string;
|
||||
|
||||
/**
|
||||
* Aliases that point to this language. Do not conflict with other languages.
|
||||
*/
|
||||
aliases: string[];
|
||||
};
|
||||
|
||||
export const languageBash: HighlightLanguage = {
|
||||
name: 'bash',
|
||||
ext: 'sh',
|
||||
aliases: ['bash', 'sh', 'shell', 'zsh'],
|
||||
};
|
||||
|
||||
export const languageCsharp: HighlightLanguage = {
|
||||
name: 'csharp',
|
||||
ext: 'cs',
|
||||
aliases: ['cs', 'csharp'],
|
||||
};
|
||||
|
||||
export const languageDocker: HighlightLanguage = {
|
||||
name: 'docker',
|
||||
ext: 'docker',
|
||||
aliases: ['docker', 'dockerfile'],
|
||||
};
|
||||
|
||||
export const languageFsharp: HighlightLanguage = {
|
||||
name: 'fsharp',
|
||||
ext: 'fs',
|
||||
aliases: ['fs', 'fsharp'],
|
||||
};
|
||||
|
||||
export const languageJavascript: HighlightLanguage = {
|
||||
name: 'javascript',
|
||||
ext: 'js',
|
||||
aliases: ['javascript', 'js'],
|
||||
};
|
||||
|
||||
export const languageKotlin: HighlightLanguage = {
|
||||
name: 'kotlin',
|
||||
ext: 'kt',
|
||||
aliases: ['kotlin', 'kt'],
|
||||
};
|
||||
|
||||
export const languageMarkdown: HighlightLanguage = {
|
||||
name: 'markdown',
|
||||
ext: 'md',
|
||||
aliases: ['markdown', 'md'],
|
||||
};
|
||||
|
||||
export const languagePython: HighlightLanguage = {
|
||||
name: 'python',
|
||||
ext: 'py',
|
||||
aliases: ['py', 'python'],
|
||||
};
|
||||
|
||||
export const languageRuby: HighlightLanguage = {
|
||||
name: 'ruby',
|
||||
ext: 'rb',
|
||||
aliases: ['rb', 'ruby'],
|
||||
};
|
||||
|
||||
export const languageRust: HighlightLanguage = {
|
||||
name: 'rust',
|
||||
ext: 'rs',
|
||||
aliases: ['rs', 'rust'],
|
||||
};
|
||||
|
||||
export const languageStylus: HighlightLanguage = {
|
||||
name: 'stylus',
|
||||
ext: 'styl',
|
||||
aliases: ['styl', 'stylus'],
|
||||
};
|
||||
|
||||
export const languageTypescript: HighlightLanguage = {
|
||||
name: 'typescript',
|
||||
ext: 'ts',
|
||||
aliases: ['ts', 'typescript'],
|
||||
};
|
||||
|
||||
export const languageYaml: HighlightLanguage = {
|
||||
name: 'yaml',
|
||||
ext: 'yml',
|
||||
aliases: ['yaml', 'yml'],
|
||||
};
|
@ -1,23 +0,0 @@
|
||||
export type HighlightLinesRange = [number, number];
|
||||
|
||||
/**
|
||||
* Resolve highlight-lines ranges from token info.
|
||||
*/
|
||||
export const resolveHighlightLines = (info: string): HighlightLinesRange[] | null => {
|
||||
// Try to match highlight-lines mark.
|
||||
const match = info.match(/{([\d,-]+)}/);
|
||||
|
||||
// No highlight-lines mark, return `null`.
|
||||
if (match === null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
// Resolve lines ranges from the highlight-lines mark.
|
||||
return match[1].split(',').map((item) => {
|
||||
const range = item.split('-');
|
||||
if (range.length === 1) {
|
||||
range.push(range[0]);
|
||||
}
|
||||
return range.map((str) => Number.parseInt(str, 10)) as HighlightLinesRange;
|
||||
});
|
||||
};
|
@ -1,45 +0,0 @@
|
||||
import type { HighlightLanguage } from './languages';
|
||||
import * as languages from './languages';
|
||||
|
||||
type LanguagesMap = Record<string, HighlightLanguage>;
|
||||
|
||||
/**
|
||||
* A key-value map to get language info from alias.
|
||||
*
|
||||
* - key: alias
|
||||
* - value: language
|
||||
*/
|
||||
let languagesMap: LanguagesMap;
|
||||
|
||||
/**
|
||||
* Lazy generate languages map.
|
||||
*/
|
||||
const getLanguagesMap = (): LanguagesMap => {
|
||||
if (!languagesMap) {
|
||||
languagesMap = Object.values(languages).reduce((result, item) => {
|
||||
item.aliases.forEach((alias) => {
|
||||
result[alias] = item;
|
||||
});
|
||||
return result;
|
||||
}, {});
|
||||
}
|
||||
|
||||
return languagesMap;
|
||||
};
|
||||
|
||||
/**
|
||||
* Resolve language for highlight from token info.
|
||||
*/
|
||||
export const resolveLanguage = (info: string): HighlightLanguage => {
|
||||
// Get user-defined language alias.
|
||||
const alias = info.match(/^([a-zA-Z]+)/)?.[1] || 'text';
|
||||
|
||||
// If the alias does not have a match in the map fallback to the alias itself.
|
||||
return (
|
||||
getLanguagesMap()[alias] ?? {
|
||||
name: alias,
|
||||
ext: alias,
|
||||
aliases: [alias],
|
||||
}
|
||||
);
|
||||
};
|
@ -1,63 +0,0 @@
|
||||
import type { PluginWithOptions } from 'markdown-it';
|
||||
import type Token from 'markdown-it/lib/token';
|
||||
import container from 'markdown-it-container';
|
||||
|
||||
import { titleToSnakeCase } from '../../../utils/string';
|
||||
import { isString } from '../../../utils/unit';
|
||||
import type { MarkdownCustomComponent, MarkdownParser } from '../types';
|
||||
|
||||
const propsRE = /(?:\s|\|)(.*?)=(.*?)(?=(\||$))/g;
|
||||
const bodyRE = /\((.*?)\)(?:=)(.*)/;
|
||||
const tagRE = /tag=(.*?)(?:&|\))/;
|
||||
const slotRE = /slot=(.*?)(?:&|\))/;
|
||||
|
||||
function renderDefault(parser: MarkdownParser, componentName: string) {
|
||||
return function (tokens: Token[], idx: number) {
|
||||
const token = tokens[idx];
|
||||
|
||||
const props: string[] = [];
|
||||
const body: string[] = [];
|
||||
|
||||
const matchedProps = token.info.trim().matchAll(propsRE);
|
||||
|
||||
for (const [propMatch, prop, value] of matchedProps) {
|
||||
if (bodyRE.test(propMatch)) {
|
||||
const [_, __, content] = propMatch.match(bodyRE) ?? [];
|
||||
const tag = propMatch.match(tagRE)?.[1] ?? 'p';
|
||||
const slot = propMatch.match(slotRE)?.[1];
|
||||
if (isString(tag) && isString(content)) {
|
||||
body.push(
|
||||
[
|
||||
`<${tag}${isString(slot) ? ` slot="${slot}"` : ''}>`,
|
||||
parser
|
||||
.render(content)
|
||||
.replace(/^<p>/, '')
|
||||
.replace(/<\/p>\n?$/, ''),
|
||||
`</${tag}>`,
|
||||
].join('\n'),
|
||||
);
|
||||
}
|
||||
} else if (isString(prop) && isString(value)) {
|
||||
props.push(`${prop}=${value}`);
|
||||
}
|
||||
}
|
||||
|
||||
if (token.nesting === 1) {
|
||||
return `<${componentName} ${props.join(' ')}>\n ${body.join('\n ')}\n`;
|
||||
} else {
|
||||
return `</${componentName}>\n`;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
export const containersPlugin: PluginWithOptions<MarkdownCustomComponent[]> = (
|
||||
parser: MarkdownParser,
|
||||
components = [],
|
||||
) => {
|
||||
for (const { name: componentName, container: options } of components) {
|
||||
const name: string = options?.name ?? titleToSnakeCase(componentName);
|
||||
const marker: string = options?.marker ?? ':';
|
||||
const render = options?.renderer?.(componentName) ?? renderDefault(parser, componentName);
|
||||
parser.use(container, name, { marker, render });
|
||||
}
|
||||
};
|
@ -1,38 +0,0 @@
|
||||
import type { PluginSimple } from 'markdown-it';
|
||||
|
||||
import { htmlBlockRule, HTMLBlockSequence } from './htmlBlockRule';
|
||||
import { htmlInlineRule } from './htmlInlineRule';
|
||||
|
||||
/**
|
||||
* Svelte reserved tags.
|
||||
*
|
||||
* @see https://svelte.dev/docs#svelte_self
|
||||
*/
|
||||
export const svelteReservedTags = [
|
||||
'svelte:self',
|
||||
'svelte:component',
|
||||
'svelte:window',
|
||||
'svelte:body',
|
||||
'svelte:head',
|
||||
'svelte:options',
|
||||
'svelte:fragment',
|
||||
'slot',
|
||||
];
|
||||
|
||||
const svelteHtmlBlockSequence: HTMLBlockSequence[] = [
|
||||
// Treat Svelte reserved tags as block tags.
|
||||
[new RegExp('^</?(' + svelteReservedTags.join('|') + ')(?=(\\s|/?>|$))', 'i'), /^$/, true],
|
||||
];
|
||||
|
||||
/**
|
||||
* Replacing the default `htmlBlock` rule to allow using custom components in markdown.
|
||||
*/
|
||||
export const customComponentPlugin: PluginSimple = (parser) => {
|
||||
// Override default html block ruler.
|
||||
parser.block.ruler.at('html_block', htmlBlockRule(svelteHtmlBlockSequence), {
|
||||
alt: ['paragraph', 'reference', 'blockquote'],
|
||||
});
|
||||
|
||||
// Override default html inline ruler.
|
||||
parser.inline.ruler.at('html_inline', htmlInlineRule);
|
||||
};
|
@ -1,163 +0,0 @@
|
||||
import type { RuleBlock } from 'markdown-it/lib/parser_block';
|
||||
|
||||
import { HTML_OPEN_CLOSE_TAG_RE } from './htmlRe';
|
||||
import { inlineTags } from './inlineTags';
|
||||
|
||||
// Forked and modified from 'markdown-it/lib/rules_block/html_block.js'
|
||||
|
||||
const blockNames = [
|
||||
'address',
|
||||
'article',
|
||||
'aside',
|
||||
'base',
|
||||
'basefont',
|
||||
'blockquote',
|
||||
'body',
|
||||
'caption',
|
||||
'center',
|
||||
'col',
|
||||
'colgroup',
|
||||
'dd',
|
||||
'details',
|
||||
'dialog',
|
||||
'dir',
|
||||
'div',
|
||||
'dl',
|
||||
'dt',
|
||||
'fieldset',
|
||||
'figcaption',
|
||||
'figure',
|
||||
'footer',
|
||||
'form',
|
||||
'frame',
|
||||
'frameset',
|
||||
'h1',
|
||||
'h2',
|
||||
'h3',
|
||||
'h4',
|
||||
'h5',
|
||||
'h6',
|
||||
'head',
|
||||
'header',
|
||||
'hr',
|
||||
'html',
|
||||
'iframe',
|
||||
'legend',
|
||||
'li',
|
||||
'link',
|
||||
'main',
|
||||
'menu',
|
||||
'menuitem',
|
||||
'nav',
|
||||
'noframes',
|
||||
'ol',
|
||||
'optgroup',
|
||||
'option',
|
||||
'p',
|
||||
'param',
|
||||
'section',
|
||||
'source',
|
||||
'summary',
|
||||
'table',
|
||||
'tbody',
|
||||
'td',
|
||||
'tfoot',
|
||||
'th',
|
||||
'thead',
|
||||
'title',
|
||||
'tr',
|
||||
'track',
|
||||
'ul',
|
||||
];
|
||||
|
||||
/**
|
||||
* An array of opening and corresponding closing sequences for html tags. The last array value
|
||||
* defines whether it can terminate a paragraph or not.
|
||||
*/
|
||||
export type HTMLBlockSequence = [RegExp, RegExp, boolean];
|
||||
|
||||
const HTML_SEQUENCES: HTMLBlockSequence[] = [
|
||||
[/^<(script|pre|style)(?=(\s|>|$))/i, /<\/(script|pre|style)>/i, true],
|
||||
[/^<!--/, /-->/, true],
|
||||
[/^<\?/, /\?>/, true],
|
||||
[/^<![A-Z]/, />/, true],
|
||||
[/^<!\[CDATA\[/, /\]\]>/, true],
|
||||
// MODIFIED HERE: Treat unknown tags as block tags (custom components), excluding known inline tags
|
||||
[new RegExp('^</?(?!(' + inlineTags.join('|') + ')(?![\\w-]))\\w[\\w-]*[\\s/>]'), /^$/, true],
|
||||
// eslint-disable-next-line import/namespace
|
||||
[new RegExp('^</?(' + blockNames.join('|') + ')(?=(\\s|/?>|$))', 'i'), /^$/, true],
|
||||
[new RegExp(HTML_OPEN_CLOSE_TAG_RE.source + '\\s*$'), /^$/, false],
|
||||
];
|
||||
|
||||
export const htmlBlockRule = (customSequences: HTMLBlockSequence[] = []): RuleBlock => {
|
||||
const sequences: HTMLBlockSequence[] = [...HTML_SEQUENCES, ...customSequences];
|
||||
|
||||
return (state, startLine, endLine, silent): boolean => {
|
||||
let i: number;
|
||||
let nextLine: number;
|
||||
let lineText: string;
|
||||
let pos = state.bMarks[startLine] + state.tShift[startLine];
|
||||
let max = state.eMarks[startLine];
|
||||
|
||||
// if it's indented more than 3 spaces, it should be a code block
|
||||
if (state.sCount[startLine] - state.blkIndent >= 4) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!state.md.options.html) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (state.src.charCodeAt(pos) !== 0x3c /* < */) {
|
||||
return false;
|
||||
}
|
||||
|
||||
lineText = state.src.slice(pos, max);
|
||||
|
||||
for (i = 0; i < sequences.length; i++) {
|
||||
if (sequences[i][0].test(lineText)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (i === sequences.length) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (silent) {
|
||||
// true if this sequence can be a terminator, false otherwise
|
||||
return sequences[i][2];
|
||||
}
|
||||
|
||||
nextLine = startLine + 1;
|
||||
|
||||
// If we are here - we detected HTML block.
|
||||
// Let's roll down till block end.
|
||||
if (!sequences[i][1].test(lineText)) {
|
||||
for (; nextLine < endLine; nextLine++) {
|
||||
if (state.sCount[nextLine] < state.blkIndent) {
|
||||
break;
|
||||
}
|
||||
|
||||
pos = state.bMarks[nextLine] + state.tShift[nextLine];
|
||||
max = state.eMarks[nextLine];
|
||||
lineText = state.src.slice(pos, max);
|
||||
|
||||
if (sequences[i][1].test(lineText)) {
|
||||
if (lineText.length !== 0) {
|
||||
nextLine++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
state.line = nextLine;
|
||||
|
||||
const token = state.push('html_block', '', 0);
|
||||
token.map = [startLine, nextLine];
|
||||
token.content = state.getLines(startLine, nextLine, state.blkIndent, true);
|
||||
|
||||
return true;
|
||||
};
|
||||
};
|
@ -1,44 +0,0 @@
|
||||
import type { RuleInline } from 'markdown-it/lib/parser_inline';
|
||||
|
||||
import { HTML_TAG_RE } from './htmlRe';
|
||||
|
||||
// Forked and modified from 'markdown-it/lib/rules_inline/html_inline.js'
|
||||
|
||||
const isLetter = (ch: number): boolean => {
|
||||
const lc = ch | 0x20; // to lower case
|
||||
return lc >= 0x61 /* a */ && lc <= 0x7a; /* z */
|
||||
};
|
||||
|
||||
export const htmlInlineRule: RuleInline = (state, silent) => {
|
||||
const pos = state.pos;
|
||||
|
||||
if (!state.md.options.html) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Check start.
|
||||
const max = state.posMax;
|
||||
if (state.src.charCodeAt(pos) !== 0x3c /* < */ || pos + 2 >= max) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Quick fail on second char.
|
||||
const ch = state.src.charCodeAt(pos + 1);
|
||||
if (ch !== 0x21 /* ! */ && ch !== 0x3f /* ? */ && ch !== 0x2f /* / */ && !isLetter(ch)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// MODIFIED HERE: Tweak the original HTML_TAG_RE.
|
||||
const match = state.src.slice(pos).match(HTML_TAG_RE);
|
||||
if (!match) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!silent) {
|
||||
const token = state.push('html_inline', '', 0);
|
||||
token.content = state.src.slice(pos, pos + match[0].length);
|
||||
}
|
||||
|
||||
state.pos += match[0].length;
|
||||
return true;
|
||||
};
|
@ -1,40 +0,0 @@
|
||||
// Forked and modified from 'markdown-it/lib/common/html_re.js'
|
||||
|
||||
// Regexps to match html elements.
|
||||
|
||||
// MODIFIED HERE: Support `@` as the first char of attr name
|
||||
const attr_name = '[a-zA-Z_:@][a-zA-Z0-9:._-]*';
|
||||
|
||||
const unquoted = '[^"\'=<>`\\x00-\\x20]+';
|
||||
const single_quoted = "'[^']*'";
|
||||
const double_quoted = '"[^"]*"';
|
||||
|
||||
const attr_value = '(?:' + unquoted + '|' + single_quoted + '|' + double_quoted + ')';
|
||||
|
||||
const attribute = '(?:\\s+' + attr_name + '(?:\\s*=\\s*' + attr_value + ')?)';
|
||||
|
||||
const open_tag = '<[A-Za-z][A-Za-z0-9\\-]*' + attribute + '*\\s*\\/?>';
|
||||
|
||||
const close_tag = '<\\/[A-Za-z][A-Za-z0-9\\-]*\\s*>';
|
||||
const comment = '<!---->|<!--(?:-?[^>-])(?:-?[^-])*-->';
|
||||
const processing = '<[?][\\s\\S]*?[?]>';
|
||||
const declaration = '<![A-Z]+\\s+[^>]*>';
|
||||
const cdata = '<!\\[CDATA\\[[\\s\\S]*?\\]\\]>';
|
||||
|
||||
export const HTML_TAG_RE = new RegExp(
|
||||
'^(?:' +
|
||||
open_tag +
|
||||
'|' +
|
||||
close_tag +
|
||||
'|' +
|
||||
comment +
|
||||
'|' +
|
||||
processing +
|
||||
'|' +
|
||||
declaration +
|
||||
'|' +
|
||||
cdata +
|
||||
')',
|
||||
);
|
||||
|
||||
export const HTML_OPEN_CLOSE_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + ')');
|
@ -1,5 +0,0 @@
|
||||
export * from './customComponentPlugin';
|
||||
export * from './htmlBlockRule';
|
||||
export * from './htmlInlineRule';
|
||||
export * from './htmlRe';
|
||||
export * from './inlineTags';
|
@ -1,73 +0,0 @@
|
||||
/**
|
||||
* According to markdown spec, all non-block html tags are treated as "inline"
|
||||
* tags (wrapped with <p></p>), including those "unknown" tags.
|
||||
*
|
||||
* Therefore, `markdown-it` processes "inline" tags and "unknown" tags in the same
|
||||
* way, and does not care if a tag is "inline" or "unknown".
|
||||
*
|
||||
* As we want to take those "unknown" tags as custom components, we should treat them as
|
||||
* "block" tags. So we have to distinguish between "inline" and "unknown" tags ourselves.
|
||||
*
|
||||
* The inline tags list comes from MDN.
|
||||
*
|
||||
* @see https://spec.commonmark.org/0.29/#raw-html
|
||||
* @see https://developer.mozilla.org/en-US/docs/Web/HTML/Inline_elements
|
||||
*/
|
||||
export const inlineTags = [
|
||||
'a',
|
||||
'abbr',
|
||||
'acronym',
|
||||
'audio',
|
||||
'b',
|
||||
'bdi',
|
||||
'bdo',
|
||||
'big',
|
||||
'br',
|
||||
'button',
|
||||
'canvas',
|
||||
'cite',
|
||||
'code',
|
||||
'data',
|
||||
'datalist',
|
||||
'del',
|
||||
'dfn',
|
||||
'em',
|
||||
'embed',
|
||||
'i',
|
||||
/* iframe is treated as HTML blocks in markdown spec */
|
||||
// 'iframe',
|
||||
'img',
|
||||
'input',
|
||||
'ins',
|
||||
'kbd',
|
||||
'label',
|
||||
'map',
|
||||
'mark',
|
||||
'meter',
|
||||
'noscript',
|
||||
'object',
|
||||
'output',
|
||||
'picture',
|
||||
'progress',
|
||||
'q',
|
||||
'ruby',
|
||||
's',
|
||||
'samp',
|
||||
'script',
|
||||
'select',
|
||||
'slot',
|
||||
'small',
|
||||
'span',
|
||||
'strong',
|
||||
'sub',
|
||||
'sup',
|
||||
'svg',
|
||||
'template',
|
||||
'textarea',
|
||||
'time',
|
||||
'u',
|
||||
'tt',
|
||||
'var',
|
||||
'video',
|
||||
'wbr',
|
||||
];
|
@ -1,6 +0,0 @@
|
||||
import type { PluginSimple } from 'markdown-it';
|
||||
import rawEmojiPlugin from 'markdown-it-emoji';
|
||||
|
||||
export const emojiPlugin: PluginSimple = (parser) => {
|
||||
return rawEmojiPlugin(parser);
|
||||
};
|
@ -1,31 +0,0 @@
|
||||
import type { PluginSimple } from 'markdown-it';
|
||||
|
||||
import type { MarkdownHeader, MarkdownParserEnv } from '../types';
|
||||
import { resolveHeadersFromTokens } from '../utils/resolveHeadersFromToken';
|
||||
|
||||
/**
|
||||
* Extracting markdown headers to `env`. Would be used for generating sidebar nav and toc.
|
||||
*/
|
||||
export const extractHeadersPlugin: PluginSimple = (parser) => {
|
||||
const level = [2, 3];
|
||||
|
||||
let headers: MarkdownHeader[];
|
||||
|
||||
// Push the rule to the end of the chain, and resolve headers from the parsed tokens.
|
||||
parser.core.ruler.push('resolveExtractHeaders', (state) => {
|
||||
headers = resolveHeadersFromTokens(state.tokens, {
|
||||
level,
|
||||
allowHtml: false,
|
||||
escapeText: false,
|
||||
});
|
||||
return true;
|
||||
});
|
||||
|
||||
// Extract headers to `env`.
|
||||
const render = parser.render.bind(parser);
|
||||
parser.render = (src, env: MarkdownParserEnv = {}) => {
|
||||
const result = render(src, env);
|
||||
env.headers = headers;
|
||||
return result;
|
||||
};
|
||||
};
|
@ -1,33 +0,0 @@
|
||||
import type { PluginSimple } from 'markdown-it';
|
||||
|
||||
import type { MarkdownParserEnv } from '../types';
|
||||
import { resolveTitleFromToken } from '../utils/resolveTitleFromToken';
|
||||
|
||||
/**
|
||||
* Extracting markdown title to parser env.
|
||||
*/
|
||||
export const extractTitlePlugin: PluginSimple = (parser) => {
|
||||
let title: string;
|
||||
|
||||
// Push the rule to the end of the chain, and resolve title from the parsed tokens.
|
||||
parser.core.ruler.push('resolveExtractTitle', (state) => {
|
||||
const tokenIdx = state.tokens.findIndex((token) => token.tag === 'h1');
|
||||
if (tokenIdx > -1) {
|
||||
title = resolveTitleFromToken(state.tokens[tokenIdx + 1], {
|
||||
escapeText: false,
|
||||
allowHtml: false,
|
||||
});
|
||||
} else {
|
||||
title = '';
|
||||
}
|
||||
return true;
|
||||
});
|
||||
|
||||
// Extract title to env.
|
||||
const render = parser.render.bind(parser);
|
||||
parser.render = (src, env: MarkdownParserEnv = {}) => {
|
||||
const result = render(src, env);
|
||||
env.title = (env.frontmatter?.title as string) ?? title;
|
||||
return result;
|
||||
};
|
||||
};
|
@ -1,26 +0,0 @@
|
||||
import type { PluginSimple } from 'markdown-it';
|
||||
|
||||
import type { MarkdownParserEnv } from '../types';
|
||||
|
||||
/**
|
||||
* Avoid rendering Svelte script/style blocks. Extract them into `env`, and hoist them root level.
|
||||
*/
|
||||
export const hoistTagsPlugin: PluginSimple = (parser) => {
|
||||
const tags = ['script', 'style', 'svelte:head'];
|
||||
const hoistTagsRegexp = new RegExp(`^<(${tags.join('|')})(?=(\\s|>|$))`, 'i');
|
||||
|
||||
const rawRule = parser.renderer.rules.html_block!;
|
||||
|
||||
parser.renderer.rules.html_block = (tokens, idx, options, env: MarkdownParserEnv, self) => {
|
||||
const content = tokens[idx].content;
|
||||
const hoistedTags = env.hoistedTags || (env.hoistedTags = []);
|
||||
|
||||
// Push hoisted tags to `env` and do not render them.
|
||||
if (hoistTagsRegexp.test(content.trim())) {
|
||||
hoistedTags.push(content);
|
||||
return '';
|
||||
}
|
||||
|
||||
return rawRule(tokens, idx, options, env, self);
|
||||
};
|
||||
};
|
@ -1,5 +0,0 @@
|
||||
export type ImportCodeTokenMeta = {
|
||||
importPath: string;
|
||||
lineStart: number;
|
||||
lineEnd?: number;
|
||||
};
|
@ -1,65 +0,0 @@
|
||||
import type { RuleBlock } from 'markdown-it/lib/parser_block';
|
||||
import path from 'path';
|
||||
|
||||
import type { ImportCodeTokenMeta } from './ImportCodeTokenMeta';
|
||||
|
||||
// Min length of the import code syntax, i.e. '@[code]()'
|
||||
const MIN_LENGTH = 9;
|
||||
|
||||
// Char codes of '@[code'
|
||||
const START_CODES = [64, 91, 99, 111, 100, 101];
|
||||
|
||||
// Regexp to match the import syntax.
|
||||
const SYNTAX_RE = /^@\[code(?:{(?:(\d+)?-(\d+)?)})?(?: ([^\]]+))?\]\(([^)]*)\)/;
|
||||
|
||||
export const createImportCodeBlockRule =
|
||||
(): RuleBlock =>
|
||||
(state, startLine, endLine, silent): boolean => {
|
||||
// If it's indented more than 3 spaces, it should be a code block.
|
||||
/* istanbul ignore if */
|
||||
if (state.sCount[startLine] - state.blkIndent >= 4) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const pos = state.bMarks[startLine] + state.tShift[startLine];
|
||||
const max = state.eMarks[startLine];
|
||||
|
||||
// Return false if the length is shorter than min length.
|
||||
if (pos + MIN_LENGTH > max) return false;
|
||||
|
||||
// Check if it's matched the start.
|
||||
for (let i = 0; i < START_CODES.length; i += 1) {
|
||||
if (state.src.charCodeAt(pos + i) !== START_CODES[i]) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// Check if it's matched the syntax.
|
||||
const match = state.src.slice(pos, max).match(SYNTAX_RE);
|
||||
if (!match) return false;
|
||||
|
||||
// Return true as we have matched the syntax.
|
||||
if (silent) return true;
|
||||
|
||||
const [, lineStart, lineEnd, info, importPath] = match;
|
||||
|
||||
const meta: ImportCodeTokenMeta = {
|
||||
importPath,
|
||||
lineStart: lineStart ? Number.parseInt(lineStart, 10) : 0,
|
||||
lineEnd: lineEnd ? Number.parseInt(lineEnd, 10) : undefined,
|
||||
};
|
||||
|
||||
// Create a import_code token.
|
||||
const token = state.push('import_code', 'code', 0);
|
||||
|
||||
// Use user specified info, or fallback to file ext.
|
||||
token.info = info ?? path.extname(meta.importPath).slice(1);
|
||||
token.markup = '```';
|
||||
token.map = [startLine, startLine + 1];
|
||||
// Store token meta to be used in renderer rule.
|
||||
token.meta = meta;
|
||||
|
||||
state.line = startLine + 1;
|
||||
|
||||
return true;
|
||||
};
|
@ -1,30 +0,0 @@
|
||||
import type { PluginSimple } from 'markdown-it';
|
||||
|
||||
import type { MarkdownParserEnv } from '../../types';
|
||||
import { createImportCodeBlockRule } from './createImportCodeBlockRule';
|
||||
import { resolveImportCode } from './resolveImportCode';
|
||||
|
||||
export const importCodePlugin: PluginSimple = (parser) => {
|
||||
// Add `import_code` block rule.
|
||||
parser.block.ruler.before('fence', 'import_code', createImportCodeBlockRule(), {
|
||||
alt: ['paragraph', 'reference', 'blockquote', 'list'],
|
||||
});
|
||||
|
||||
// Add `import_code` renderer rule.
|
||||
parser.renderer.rules.import_code = (tokens, idx, options, env: MarkdownParserEnv, slf) => {
|
||||
const token = tokens[idx];
|
||||
|
||||
// Use imported code as token content.
|
||||
const { importFilePath, importCode } = resolveImportCode(token.meta, env);
|
||||
token.content = importCode;
|
||||
|
||||
// Extract imported files to env.
|
||||
if (importFilePath) {
|
||||
const importedFiles = env.importedFiles || (env.importedFiles = []);
|
||||
importedFiles.push(importFilePath);
|
||||
}
|
||||
|
||||
// Render the `import_code` token as a fence token.
|
||||
return parser.renderer.rules.fence!(tokens, idx, options, env, slf);
|
||||
};
|
||||
};
|
@ -1,4 +0,0 @@
|
||||
export * from './createImportCodeBlockRule';
|
||||
export * from './importCodePlugin';
|
||||
export * from './ImportCodeTokenMeta';
|
||||
export * from './resolveImportCode';
|
@ -1,47 +0,0 @@
|
||||
import fs from 'fs';
|
||||
import path from 'path';
|
||||
|
||||
import type { MarkdownParserEnv } from '../../types';
|
||||
import type { ImportCodeTokenMeta } from './ImportCodeTokenMeta';
|
||||
|
||||
export const resolveImportCode = (
|
||||
{ importPath, lineStart, lineEnd }: ImportCodeTokenMeta,
|
||||
{ filePath }: MarkdownParserEnv,
|
||||
): {
|
||||
importFilePath: string | null;
|
||||
importCode: string;
|
||||
} => {
|
||||
let importFilePath = importPath;
|
||||
|
||||
if (!path.isAbsolute(importPath)) {
|
||||
// If the importPath is relative path, we need to resolve it according to the markdown filePath.
|
||||
if (!filePath) {
|
||||
return {
|
||||
importFilePath: null,
|
||||
importCode: 'Error when resolving path',
|
||||
};
|
||||
}
|
||||
importFilePath = path.resolve(filePath, '..', importPath);
|
||||
}
|
||||
|
||||
// Check file existence.
|
||||
if (!fs.existsSync(importFilePath)) {
|
||||
return {
|
||||
importFilePath,
|
||||
importCode: 'File not found',
|
||||
};
|
||||
}
|
||||
|
||||
// Read file content.
|
||||
const fileContent = fs.readFileSync(importFilePath).toString();
|
||||
|
||||
// Resolve partial import.
|
||||
return {
|
||||
importFilePath,
|
||||
importCode: fileContent
|
||||
.split('\n')
|
||||
.slice(lineStart ? lineStart - 1 : lineStart, lineEnd)
|
||||
.join('\n')
|
||||
.replace(/\n?$/, '\n'),
|
||||
};
|
||||
};
|
@ -1,12 +0,0 @@
|
||||
export * from './anchorPlugin';
|
||||
export * from './codePlugin';
|
||||
export * from './containersPlugin';
|
||||
export * from './customComponentPlugin';
|
||||
export * from './emojiPlugin';
|
||||
export * from './extractHeadersPlugin';
|
||||
export * from './extractTitlePlugin';
|
||||
export * from './hoistTagsPlugin';
|
||||
export * from './importCodePlugin';
|
||||
export * from './linksPlugin';
|
||||
export * from './shikiPlugin';
|
||||
export * from './tocPlugin';
|
@ -1,72 +0,0 @@
|
||||
import { lstatSync } from 'fs';
|
||||
import { type PluginSimple } from 'markdown-it';
|
||||
import { dirname, relative, resolve } from 'path';
|
||||
|
||||
import { isLinkExternal } from '../utils/isLink';
|
||||
|
||||
const ROUTES_DIR = resolve(process.cwd(), 'src/routes');
|
||||
|
||||
const restParamsRe = /\[\.\.\..*?\]/g;
|
||||
|
||||
/**
|
||||
* Resolves link URLs.
|
||||
*/
|
||||
export const linksPlugin: PluginSimple = (parser) => {
|
||||
// Attrs that going to be added to external links.
|
||||
const externalAttrs = {
|
||||
target: '_blank',
|
||||
rel: 'noopener noreferrer',
|
||||
};
|
||||
|
||||
parser.renderer.rules.link_open = (tokens, idx, _, env) => {
|
||||
const token = tokens[idx];
|
||||
const hrefIndex = token.attrIndex('href');
|
||||
|
||||
const props: string[] = [];
|
||||
|
||||
if (hrefIndex >= 0) {
|
||||
const hrefAttr = token.attrs?.[hrefIndex];
|
||||
const hrefLink = hrefAttr![1];
|
||||
|
||||
const internalLinkMatch = hrefLink.match(/^((?:.*)(?:\/|\.md|\.html))(#.*)?$/);
|
||||
|
||||
if (isLinkExternal(hrefLink, '/')) {
|
||||
Object.entries(externalAttrs ?? {}).forEach(([key, val]) => {
|
||||
token.attrSet(key, val);
|
||||
});
|
||||
} else if (internalLinkMatch) {
|
||||
const rawPath = decodeURI(internalLinkMatch?.[1]);
|
||||
const rawHash = internalLinkMatch?.[2] ?? '';
|
||||
|
||||
const { filePath } = env;
|
||||
|
||||
const absolutePath = rawPath?.startsWith('/')
|
||||
? '.' + rawPath
|
||||
: resolve(lstatSync(filePath).isDirectory() ? filePath : dirname(filePath), rawPath);
|
||||
|
||||
const slug = relative(ROUTES_DIR, absolutePath)
|
||||
.replace(restParamsRe, '')
|
||||
.replace(/\/\+page/, '')
|
||||
.replace(/\.(md|html)/, '');
|
||||
|
||||
// Set new path.
|
||||
hrefAttr![1] = '/' + slug + rawHash;
|
||||
|
||||
const links = env.links || (env.links = []);
|
||||
links.push(hrefAttr![1]);
|
||||
}
|
||||
|
||||
if (token.attrs) {
|
||||
for (const [name, value] of token.attrs) {
|
||||
props.push(`${name}="${value}"`);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return `<Link ${props.filter(Boolean).join(' ')}>${token.content}`;
|
||||
};
|
||||
|
||||
parser.renderer.rules.link_close = () => {
|
||||
return '</Link>';
|
||||
};
|
||||
};
|
@ -1,17 +0,0 @@
|
||||
import { type PluginSimple } from 'markdown-it';
|
||||
import { type HighlighterOptions, getHighlighter, renderToHtml } from 'shiki';
|
||||
|
||||
export const createShikiPlugin = async (options?: HighlighterOptions) => {
|
||||
const highlighter = await getHighlighter({
|
||||
theme: 'material-palenight',
|
||||
langs: ["bash", "javascript", "typescript", "svelte", "markdown", "html", "diff", "css"],
|
||||
...options,
|
||||
});
|
||||
|
||||
return ((parser) => {
|
||||
parser.options.highlight = (code, lang) => {
|
||||
const tokens = highlighter.codeToThemedTokens(code, lang);
|
||||
return renderToHtml(tokens);
|
||||
};
|
||||
}) as PluginSimple;
|
||||
};
|
@ -1,41 +0,0 @@
|
||||
import type { RuleBlock } from 'markdown-it/lib/parser_block';
|
||||
|
||||
/**
|
||||
* Forked and modified from `markdown-it-toc-done-right`.
|
||||
*
|
||||
* - Remove the `inlineOptions` support.
|
||||
* - Use `markdown-it` default renderer to render token whenever possible.
|
||||
*
|
||||
* @see https://github.com/nagaozen/markdown-it-toc-done-right
|
||||
*/
|
||||
export const createTocBlockRule = ({ pattern }: { pattern: RegExp }): RuleBlock => {
|
||||
return (state, startLine, endLine, silent): boolean => {
|
||||
// If it's indented more than 3 spaces, it should be a code block.
|
||||
if (state.sCount[startLine] - state.blkIndent >= 4) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const pos = state.bMarks[startLine] + state.tShift[startLine];
|
||||
const max = state.eMarks[startLine];
|
||||
|
||||
/**
|
||||
* Use whitespace as a line tokenizer and extract the first token to test against the
|
||||
* placeholder anchored pattern, rejecting if `false`.
|
||||
*/
|
||||
const lineFirstToken = state.src.slice(pos, max).split(' ')[0];
|
||||
if (!pattern.test(lineFirstToken)) return false;
|
||||
|
||||
if (silent) return true;
|
||||
|
||||
state.line = startLine + 1;
|
||||
|
||||
const tokenOpen = state.push('toc_open', 'TableOfContents', 1);
|
||||
tokenOpen.markup = '';
|
||||
tokenOpen.map = [startLine, state.line];
|
||||
|
||||
const tokenClose = state.push('toc_close', 'TableOfContents', -1);
|
||||
tokenClose.markup = '';
|
||||
|
||||
return true;
|
||||
};
|
||||
};
|
@ -1,2 +0,0 @@
|
||||
export * from './createTocBlockRule';
|
||||
export * from './tocPlugin';
|
@ -1,51 +0,0 @@
|
||||
import type { PluginSimple } from 'markdown-it';
|
||||
|
||||
import type { MarkdownHeader } from '../../types';
|
||||
import { resolveHeadersFromTokens } from '../../utils/resolveHeadersFromToken';
|
||||
import { createTocBlockRule } from './createTocBlockRule';
|
||||
|
||||
/**
|
||||
* Generate table of contents.
|
||||
*
|
||||
* Forked and modified from `markdown-it-toc-done-right`:
|
||||
*
|
||||
* - Allows `html_inline` tags in headings to support custom components.
|
||||
* - Allows custom tags for links.
|
||||
* - Code refactor and optimizations.
|
||||
*
|
||||
* @see https://github.com/nagaozen/markdown-it-toc-done-right
|
||||
*/
|
||||
export const tocPlugin: PluginSimple = (parser) => {
|
||||
const pattern = /^\[\[toc\]\]$/i;
|
||||
const level = [2, 3];
|
||||
|
||||
let headers: MarkdownHeader[];
|
||||
|
||||
// Push the rule to the end of the chain, and resolve headers from the parsed tokens.
|
||||
parser.core.ruler.push('resolveTocHeaders', (state) => {
|
||||
headers = resolveHeadersFromTokens(state.tokens, {
|
||||
level,
|
||||
allowHtml: true,
|
||||
escapeText: true,
|
||||
});
|
||||
return true;
|
||||
});
|
||||
|
||||
// Add toc syntax as a block rule.
|
||||
parser.block.ruler.before('heading', 'toc', createTocBlockRule({ pattern }), {
|
||||
alt: ['paragraph', 'reference', 'blockquote'],
|
||||
});
|
||||
|
||||
// Custom toc_body render rule.
|
||||
parser.renderer.rules.toc_open = () => {
|
||||
if (!headers) {
|
||||
return '';
|
||||
}
|
||||
|
||||
return `<TableOfContents headers={\`${JSON.stringify(headers, [
|
||||
'title',
|
||||
'slug',
|
||||
'children',
|
||||
])}\`}>`;
|
||||
};
|
||||
};
|
@ -1,120 +0,0 @@
|
||||
import type MarkdownIt from 'markdown-it';
|
||||
import type Token from 'markdown-it/lib/token';
|
||||
|
||||
export type MarkdownParser = MarkdownIt;
|
||||
|
||||
export type ParseMarkdownOptions = {
|
||||
mode?: string;
|
||||
baseUrl?: string;
|
||||
escapeConstants?: boolean;
|
||||
define?: Record<string, unknown>;
|
||||
globalComponentFiles?: string[];
|
||||
topLevelHtmlTags?: AddTopLevelHtmlTags;
|
||||
};
|
||||
|
||||
export type AddTopLevelHtmlTags = (data: {
|
||||
fileName: string;
|
||||
filePath: string;
|
||||
meta: MarkdownMeta;
|
||||
}) => string[] | undefined | null;
|
||||
|
||||
export type InlineElementRule = 'emphasized' | 'image' | 'strikethrough' | 'strong';
|
||||
|
||||
export type BlockElementRule =
|
||||
| 'blockquote'
|
||||
| 'heading'
|
||||
| 'list_item'
|
||||
| 'ordered_list'
|
||||
| 'paragraph'
|
||||
| 'table'
|
||||
| 'bullet_list';
|
||||
|
||||
export type MarkdownInlineComponent = {
|
||||
name: string;
|
||||
type: 'inline';
|
||||
rule: InlineElementRule;
|
||||
};
|
||||
|
||||
export type MarkdownBlockComponent = {
|
||||
name: string;
|
||||
type: 'block';
|
||||
rule: BlockElementRule;
|
||||
};
|
||||
|
||||
export type MarkdownCustomComponent = {
|
||||
name: string;
|
||||
type: 'custom';
|
||||
container?: MarkdownComponentContainer;
|
||||
};
|
||||
|
||||
export type MarkdownComponentContainer = {
|
||||
name?: string;
|
||||
marker?: string;
|
||||
renderer?(componentName: string): (tokens: Token[], idx: number) => string;
|
||||
};
|
||||
|
||||
export type MarkdownComponents = (
|
||||
| MarkdownInlineComponent
|
||||
| MarkdownBlockComponent
|
||||
| MarkdownCustomComponent
|
||||
)[];
|
||||
|
||||
export type MarkdownMeta = {
|
||||
title: string;
|
||||
description: string;
|
||||
excerpt: string;
|
||||
headers: MarkdownHeader[];
|
||||
frontmatter: MarkdownFrontmatter;
|
||||
lastUpdated: number;
|
||||
};
|
||||
|
||||
export type MarkdownFrontmatter = Record<string, unknown>;
|
||||
|
||||
export type MarkdownHeader = {
|
||||
level: number;
|
||||
title: string;
|
||||
slug: string;
|
||||
children?: MarkdownHeader[];
|
||||
};
|
||||
|
||||
export type MarkdownLinks = string[];
|
||||
|
||||
export type ParsedMarkdownResult = {
|
||||
content: string;
|
||||
meta: MarkdownMeta;
|
||||
html: string;
|
||||
links: MarkdownLinks;
|
||||
importedFiles: string[];
|
||||
env: MarkdownParserEnv;
|
||||
};
|
||||
|
||||
/**
|
||||
* Metadata provided to markdown parser.
|
||||
*/
|
||||
export type MarkdownParserEnvInput = {
|
||||
/** Absolute system file path of the markdown file. */
|
||||
filePath?: string | null;
|
||||
/** Frontmatter of the markdown file. */
|
||||
frontmatter?: MarkdownFrontmatter;
|
||||
};
|
||||
|
||||
/**
|
||||
* Resources extracted from markdown parser.
|
||||
*/
|
||||
export type MarkdownParserEnvOutput = {
|
||||
/** Headers that are extracted by `extractHeadersPlugin`. */
|
||||
headers?: MarkdownHeader[];
|
||||
/** Imported files that are extracted by `importCodePlugin`. */
|
||||
importedFiles?: string[];
|
||||
/** Hoisted `<script>` and `<style>` tags. */
|
||||
hoistedTags?: string[];
|
||||
/** Links that are extracted by `linksPlugin`. */
|
||||
links?: MarkdownLinks;
|
||||
/** Title that is extracted by `extractTitlePlugin`. */
|
||||
title?: string;
|
||||
};
|
||||
|
||||
/**
|
||||
* The `env` object to be passed to `markdown-it` render function.
|
||||
*/
|
||||
export type MarkdownParserEnv = MarkdownParserEnvInput & MarkdownParserEnvOutput;
|
@ -1,43 +0,0 @@
|
||||
const htmlEscapeMap = {
|
||||
'&': '&',
|
||||
'<': '<',
|
||||
'>': '>',
|
||||
"'": ''',
|
||||
'"': '"',
|
||||
};
|
||||
|
||||
const htmlEscapeRegexp = /[&<>'"]/g;
|
||||
|
||||
export const htmlEscape = (str: string): string =>
|
||||
str.replace(htmlEscapeRegexp, (char) => htmlEscapeMap[char]);
|
||||
|
||||
const htmlUnescapeMap = {
|
||||
'&': '&',
|
||||
'&': '&',
|
||||
'<': '<',
|
||||
'<': '<',
|
||||
'>': '>',
|
||||
'>': '>',
|
||||
''': "'",
|
||||
''': "'",
|
||||
'"': '"',
|
||||
'"': '"',
|
||||
};
|
||||
|
||||
const htmlUnescapeRegexp = /&(amp|#38|lt|#60|gt|#62|apos|#39|quot|#34);/g;
|
||||
|
||||
export const htmlUnescape = (str: string): string =>
|
||||
str.replace(htmlUnescapeRegexp, (char) => htmlUnescapeMap[char]);
|
||||
|
||||
const TEMPLATE_TAG_RE =
|
||||
/(\{#(if|each|await|key).*\})|(\{:(else|then|catch).*\})|(\{\/(if|each|key|await)\})|(\{@(html|debug).*\})/gim;
|
||||
export function commentOutTemplateTags(source: string) {
|
||||
return source.replace(TEMPLATE_TAG_RE, (match) => {
|
||||
return `<!--&%& ${match} &%&-->`;
|
||||
});
|
||||
}
|
||||
|
||||
const TEMPLATE_TAG_COMMENT_RE = /(<!--&%&\s)|(\s&%&-->)/gim;
|
||||
export function uncommentTemplateTags(source: string) {
|
||||
return source.replace(TEMPLATE_TAG_COMMENT_RE, '');
|
||||
}
|
@ -1,25 +0,0 @@
|
||||
/**
|
||||
* Determine if a link is a http link or not.
|
||||
*
|
||||
* - http://github.com
|
||||
* - https://github.com
|
||||
* - //github.com
|
||||
*/
|
||||
export const isLinkHttp = (link: string): boolean => /^(https?:)?\/\//.test(link);
|
||||
|
||||
/**
|
||||
* Determine if a link is external or not.
|
||||
*/
|
||||
export const isLinkExternal = (link: string, base = '/'): boolean => {
|
||||
// http link
|
||||
if (isLinkHttp(link)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
// absolute link that does not start with `base`
|
||||
if (link.startsWith('/') && !link.startsWith(base)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
};
|
@ -1,25 +0,0 @@
|
||||
/**
|
||||
* Global constants and env variables will be statically replaced by Vite in build mode. This
|
||||
* util helps avoid that by inserting escape sequences.
|
||||
*
|
||||
* @see https://vitejs.dev/guide/env-and-mode.html#production-replacement
|
||||
*/
|
||||
export function preventViteReplace(source: string, define?: Record<string, unknown>): string {
|
||||
source = source
|
||||
.replace(/\bimport\.meta/g, 'import.<wbr/>meta')
|
||||
.replace(/\bprocess\.env/g, 'process.<wbr/>env');
|
||||
|
||||
// Also avoid replacing defines.
|
||||
if (define) {
|
||||
const regex = new RegExp(
|
||||
`\\b(${Object.keys(define)
|
||||
.map((key) => key.replace(/[-[\]/{}()*+?.\\^$|]/g, '\\$&'))
|
||||
.join('|')})`,
|
||||
'g',
|
||||
);
|
||||
|
||||
source = source.replace(regex, (_) => `${_[0]}<wbr/>${_.slice(1)}`);
|
||||
}
|
||||
|
||||
return source;
|
||||
}
|
@ -1,87 +0,0 @@
|
||||
import type Token from 'markdown-it/lib/token';
|
||||
|
||||
import type { MarkdownHeader } from '../types';
|
||||
import { resolveTitleFromToken } from './resolveTitleFromToken';
|
||||
import { slugify } from './slugify';
|
||||
|
||||
/**
|
||||
* Resolve headers from `markdown-it` tokens.
|
||||
*/
|
||||
export const resolveHeadersFromTokens = (
|
||||
tokens: Token[],
|
||||
{
|
||||
level,
|
||||
allowHtml,
|
||||
escapeText,
|
||||
}: {
|
||||
level: number[];
|
||||
allowHtml: boolean;
|
||||
escapeText: boolean;
|
||||
},
|
||||
): MarkdownHeader[] => {
|
||||
const headers: MarkdownHeader[] = [];
|
||||
|
||||
// A temp headers stack for generating the headers tree.
|
||||
const stack: MarkdownHeader[] = [];
|
||||
|
||||
// Push a header to the headers tree.
|
||||
const push = (header: MarkdownHeader): void => {
|
||||
while (stack.length !== 0 && header.level <= stack[0].level) {
|
||||
stack.shift();
|
||||
}
|
||||
|
||||
if (stack.length === 0) {
|
||||
headers.push(header);
|
||||
stack.push(header);
|
||||
} else {
|
||||
(stack[0].children ??= []).push(header);
|
||||
stack.unshift(header);
|
||||
}
|
||||
};
|
||||
|
||||
tokens.forEach((_, idx) => {
|
||||
const token = tokens[idx];
|
||||
|
||||
// If the token type does not match, skip.
|
||||
if (token?.type !== 'heading_open') {
|
||||
return;
|
||||
}
|
||||
|
||||
// Get the level from the tag, `h1 -> 1`.
|
||||
const headerLevel = Number.parseInt(token.tag.slice(1), 10);
|
||||
|
||||
// If the level should not be extracted, skip.
|
||||
if (!level.includes(headerLevel)) {
|
||||
return;
|
||||
}
|
||||
|
||||
// The next token of 'heading_open' contains the heading content.
|
||||
const nextToken = tokens[idx + 1];
|
||||
|
||||
// If the next token does not exist, skip.
|
||||
if (!nextToken) {
|
||||
return;
|
||||
}
|
||||
|
||||
const title = resolveTitleFromToken(nextToken, {
|
||||
allowHtml,
|
||||
escapeText,
|
||||
});
|
||||
|
||||
/**
|
||||
* The id of the heading anchor is the slugified result of `markdown-it-anchor` if the id
|
||||
* does not exist, we'll slugify the title ourselves.
|
||||
*/
|
||||
const slug = token.attrGet('id') ?? slugify(title);
|
||||
|
||||
// Push the header to tree.
|
||||
push({
|
||||
level: headerLevel,
|
||||
title,
|
||||
slug,
|
||||
children: [],
|
||||
});
|
||||
});
|
||||
|
||||
return headers;
|
||||
};
|
@ -1,52 +0,0 @@
|
||||
import type Token from 'markdown-it/lib/token';
|
||||
|
||||
import { htmlEscape } from './htmlEscape';
|
||||
|
||||
/**
|
||||
* Resolve header title from `markdown-it` token. Typically using the next token of
|
||||
* `heading_open` token.
|
||||
*/
|
||||
export const resolveTitleFromToken = (
|
||||
token: Token,
|
||||
{
|
||||
allowHtml,
|
||||
escapeText,
|
||||
}: {
|
||||
allowHtml: boolean;
|
||||
escapeText: boolean;
|
||||
},
|
||||
): string => {
|
||||
// Children of the token contains the parsed result of the heading title.
|
||||
const children = token.children ?? [];
|
||||
|
||||
// Type of tokens to be included in the heading title.
|
||||
const titleTokenTypes = ['text', 'emoji', 'code_inline'];
|
||||
|
||||
// Include 'html_inline' or not.
|
||||
if (allowHtml) {
|
||||
titleTokenTypes.push('html_inline');
|
||||
}
|
||||
|
||||
// Filter the token type to be included in the title.
|
||||
const titleTokens = children.filter(
|
||||
(item) =>
|
||||
titleTokenTypes.includes(item.type) &&
|
||||
// Filter permalink symbol that generated by `markdown-it-anchor`.
|
||||
!item.meta?.isPermalinkSymbol,
|
||||
);
|
||||
|
||||
// Get title from tokens.
|
||||
return titleTokens
|
||||
.reduce((result, item) => {
|
||||
if (escapeText) {
|
||||
// Escape the content of 'code_inline' and 'text'.
|
||||
if (item.type === 'code_inline' || item.type === 'text') {
|
||||
return `${result}${htmlEscape(item.content)}`;
|
||||
}
|
||||
}
|
||||
|
||||
// Keep the content of 'emoji' and 'html_inline'.
|
||||
return `${result}${item.content}`;
|
||||
}, '')
|
||||
.trim();
|
||||
};
|
@ -1,22 +0,0 @@
|
||||
// eslint-disable-next-line no-control-regex
|
||||
const rControl = /[\u0000-\u001f]/g;
|
||||
const rSpecial = /[\s~`!@#$%^&*()\-_+=[\]{}|\\;:"'“”‘’<>,.?/]+/g;
|
||||
const rCombining = /[\u0300-\u036F]/g;
|
||||
|
||||
export const slugify = (str: string): string =>
|
||||
str
|
||||
.normalize('NFKD')
|
||||
// Remove accents
|
||||
.replace(rCombining, '')
|
||||
// Remove control characters
|
||||
.replace(rControl, '')
|
||||
// Replace special characters
|
||||
.replace(rSpecial, '-')
|
||||
// Remove continuos separators
|
||||
.replace(/-{2,}/g, '-')
|
||||
// Remove prefixing and trailing separators
|
||||
.replace(/^-+|-+$/g, '')
|
||||
// Ensure it doesn't start with a number (#121)
|
||||
.replace(/^(\d)/, '_$1')
|
||||
// Lowercase
|
||||
.toLowerCase();
|
@ -1,10 +0,0 @@
|
||||
{
|
||||
"extends": "../../tsconfig-build.json",
|
||||
"compilerOptions": {
|
||||
"baseUrl": ".",
|
||||
"outDir": "../../node",
|
||||
"declarationDir": "../../node-types",
|
||||
"lib": ["es2019", "dom"]
|
||||
},
|
||||
"include": ["**/*.ts"]
|
||||
}
|
@ -1,25 +0,0 @@
|
||||
import { readFileSync } from 'fs';
|
||||
import { resolve } from 'path';
|
||||
|
||||
import { isUndefined } from './unit';
|
||||
|
||||
let isLocal;
|
||||
export function isLocalEnv() {
|
||||
if (!isUndefined(isLocal)) return isLocal;
|
||||
|
||||
try {
|
||||
const pkgPath = resolve(process.cwd(), 'package.json');
|
||||
if (pkgPath.endsWith('kit-docs/package.json')) {
|
||||
const pkg = readFileSync(pkgPath).toString();
|
||||
if (/"name": "@svelteness\/kit-docs"/.test(pkg)) {
|
||||
isLocal = true;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
} catch (e) {
|
||||
// no-op
|
||||
}
|
||||
|
||||
isLocal = false;
|
||||
return false;
|
||||
}
|
@ -1,107 +0,0 @@
|
||||
import { normalizePath } from '@rollup/pluginutils';
|
||||
import { createHash } from 'crypto';
|
||||
import { createReadStream, readdirSync, statSync } from 'fs';
|
||||
import LRUCache from 'lru-cache';
|
||||
import { resolve } from 'path';
|
||||
|
||||
export function checksumFile(path: string): Promise<string> {
|
||||
return new Promise((resolve, reject) => {
|
||||
const hash = createHash('sha256');
|
||||
const stream = createReadStream(path);
|
||||
stream.on('error', (err) => reject(err));
|
||||
stream.on('data', (chunk) => hash.update(chunk));
|
||||
stream.on('end', () => resolve(hash.digest('hex')));
|
||||
});
|
||||
}
|
||||
|
||||
const ignoreFileRE = /^(\.|_)/;
|
||||
export function readDirDeepSync(dir: string, options: { maxDepth?: number; _depth?: number } = {}) {
|
||||
const depth = options._depth ?? 0;
|
||||
|
||||
if (depth === options.maxDepth) return [];
|
||||
|
||||
const files: string[] = [];
|
||||
|
||||
for (const file of readdirSync(dir)) {
|
||||
const filePath = resolve(dir, file);
|
||||
const stat = statSync(filePath);
|
||||
|
||||
if (stat.isDirectory()) {
|
||||
files.push(
|
||||
...readDirDeepSync(filePath, {
|
||||
...options,
|
||||
_depth: depth + 1,
|
||||
}),
|
||||
);
|
||||
} else if (!ignoreFileRE.test(file)) {
|
||||
files.push(normalizePath(filePath));
|
||||
}
|
||||
}
|
||||
|
||||
return files;
|
||||
}
|
||||
|
||||
const fileOrderRE = /\[\.\.\.(\d*?)(_|=|\])/;
|
||||
const sortFilesCache = new LRUCache<string, number>({ max: 1024 });
|
||||
export function sortOrderedFiles(files: string[]) {
|
||||
return files.sort((fileA, fileB) => {
|
||||
const cacheKey = fileA + fileB;
|
||||
const cache = (result: number) => sortFilesCache.set(cacheKey, result);
|
||||
|
||||
if (sortFilesCache.has(cacheKey)) {
|
||||
return sortFilesCache.get(cacheKey)!;
|
||||
}
|
||||
|
||||
const tokensA = fileA.split('/').slice(1);
|
||||
const tokensB = fileB.split('/').slice(1);
|
||||
|
||||
const len = Math.max(tokensA.length, tokensB.length);
|
||||
|
||||
for (let i = 0; i < len; i++) {
|
||||
if (!(i in tokensA)) {
|
||||
cache(-1);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (!(i in tokensB)) {
|
||||
cache(1);
|
||||
return 1;
|
||||
}
|
||||
|
||||
const tokenA = tokensA[i].toLowerCase();
|
||||
const tokenB = tokensB[i].toLowerCase();
|
||||
|
||||
const tokenAOrderNo = tokensA[i].match(fileOrderRE)?.[1];
|
||||
const tokenBOrderNo = tokensB[i].match(fileOrderRE)?.[1];
|
||||
|
||||
if (tokenAOrderNo && tokenBOrderNo) {
|
||||
const result = parseInt(tokenAOrderNo) - parseInt(tokenBOrderNo);
|
||||
if (result !== 0) {
|
||||
cache(result);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
if (tokenA === tokenB) {
|
||||
continue;
|
||||
}
|
||||
|
||||
const isTokenADir = tokenA[tokenA.length - 1] === '/';
|
||||
const isTokenBDir = tokenB[tokenB.length - 1] === '/';
|
||||
|
||||
let result;
|
||||
|
||||
if (isTokenADir === isTokenBDir) {
|
||||
result = tokenA < tokenB ? -1 : 1;
|
||||
} else {
|
||||
result = isTokenADir ? 1 : -1;
|
||||
}
|
||||
|
||||
cache(result);
|
||||
return result;
|
||||
}
|
||||
|
||||
cache(0);
|
||||
return 0;
|
||||
});
|
||||
}
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user