From: Bjørn Erik Pedersen Date: Fri, 20 Oct 2023 07:42:39 +0000 (+0200) Subject: Squashed 'docs/' changes from 7ef2dbce4..cb18a5183 X-Git-Url: http://git.maquefel.me/?a=commitdiff_plain;h=e509cac533600cf4fa8382c9cdab78ddd82db688;p=brevno-suite%2Fhugo Squashed 'docs/' changes from 7ef2dbce4..cb18a5183 cb18a5183 Fix broken link 07a0198bf Config: Place Google Analytics tag ID under the services key 4bf0c719f Fix typo 50d8ad1af Fix muiltilingual menu definition instructions 1a32519a9 Fix typos 6f34ca8e0 Explain usage of front matter to target a template 5bd977257 Improve goldmark config docs 447632938 Remove Docker notes from installation instructions 84741d173 Update reference to hugo.work 0338d7c71 Fix menu template f5d2f5ed4 Fix typos in content/en/functions/fmt a3a40ff99 Add return type to functions 85ac3e779 Remove outdated feature image d47d889e4 Fix signatures 7551ba28f Document safe.JSStr function e77993be0 Document keyVals function 4dba20db3 Update theme babf91544 Update echoparam 8c8203efa Adjust related functions 4cb1b30fc Fix example ba95eca64 Improve showcase prose 5d3dcf366 Add Overmind Studios showcase 8d634ac70 Change code blocks from indented to fenced cfab978e6 Add missing code fences 407dd5c47 Limit related pages for functions to other functions 9fa67d981 Fix .Site.LastChange doc 393aa16d0 netlify: Hugo 0.119.0 f864af97a docs: Even more about images.Process 9d772d5f0 docs: More about images.Process bc655f869 docs: Regen docshelper 41c3536d1 Merge commit '9aec42c5452b3eb224888c50ba1c3f3b68a447e9' 918ed53f4 Add images.Process filter 573645883 Add $image.Process a1151b0fd Add images.Opacity filter git-subtree-dir: docs git-subtree-split: cb18a5183fc62f301ffde50b8c39f03e4b897aec --- diff --git a/_vendor/github.com/gohugoio/gohugoioTheme/assets/css/_social-icons.css b/_vendor/github.com/gohugoio/gohugoioTheme/assets/css/_social-icons.css index 04ea11ec5..6cfa7b1b4 100644 --- a/_vendor/github.com/gohugoio/gohugoioTheme/assets/css/_social-icons.css +++ b/_vendor/github.com/gohugoio/gohugoioTheme/assets/css/_social-icons.css @@ -1,5 +1,8 @@ -.facebook, .twitter, .instagram, .youtube { - fill: #BABABA; +.facebook, +.twitter, +.instagram, +.youtube { + fill: #bababa; } .facebook:hover { fill: #3b5998; @@ -10,10 +13,9 @@ } .twitter:hover { - fill: #BABABA; + fill: #bababa; } - .instagram:hover { fill: #e95950; } @@ -21,3 +23,30 @@ .youtube:hover { fill: #bb0000; } + +.mstdn { + display: inline-block; + background-color: #282c37; + color: #d9e1e8; + text-decoration: none; + padding: 4px 10px 4px 30px; + border-radius: 4px; + font-size: 16px; + background-image: url("data:image/svg+xml;charset=utf8,%3Csvg%20xmlns%3D%22http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%22%20width%3D%2261.076954mm%22%20height%3D%2265.47831mm%22%20viewBox%3D%220%200%20216.4144%20232.00976%22%3E%3Cpath%20d%3D%22M211.80734%20139.0875c-3.18125%2016.36625-28.4925%2034.2775-57.5625%2037.74875-15.15875%201.80875-30.08375%203.47125-45.99875%202.74125-26.0275-1.1925-46.565-6.2125-46.565-6.2125%200%202.53375.15625%204.94625.46875%207.2025%203.38375%2025.68625%2025.47%2027.225%2046.39125%2027.9425%2021.11625.7225%2039.91875-5.20625%2039.91875-5.20625l.8675%2019.09s-14.77%207.93125-41.08125%209.39c-14.50875.7975-32.52375-.365-53.50625-5.91875C9.23234%20213.82%201.40609%20165.31125.20859%20116.09125c-.365-14.61375-.14-28.39375-.14-39.91875%200-50.33%2032.97625-65.0825%2032.97625-65.0825C49.67234%203.45375%2078.20359.2425%20107.86484%200h.72875c29.66125.2425%2058.21125%203.45375%2074.8375%2011.09%200%200%2032.975%2014.7525%2032.975%2065.0825%200%200%20.41375%2037.13375-4.59875%2062.915%22%20fill%3D%22%233088d4%22%2F%3E%3Cpath%20d%3D%22M177.50984%2080.077v60.94125h-24.14375v-59.15c0-12.46875-5.24625-18.7975-15.74-18.7975-11.6025%200-17.4175%207.5075-17.4175%2022.3525v32.37625H96.20734V85.42325c0-14.845-5.81625-22.3525-17.41875-22.3525-10.49375%200-15.74%206.32875-15.74%2018.7975v59.15H38.90484V80.077c0-12.455%203.17125-22.3525%209.54125-29.675%206.56875-7.3225%2015.17125-11.07625%2025.85-11.07625%2012.355%200%2021.71125%204.74875%2027.8975%2014.2475l6.01375%2010.08125%206.015-10.08125c6.185-9.49875%2015.54125-14.2475%2027.8975-14.2475%2010.6775%200%2019.28%203.75375%2025.85%2011.07625%206.36875%207.3225%209.54%2017.22%209.54%2029.675%22%20fill%3D%22%23fff%22%2F%3E%3C%2Fsvg%3E"); + background-size: 16px; + background-repeat: no-repeat; + background-position: top 50% left 8px; + transition: all 0.5s; +} +.mstdn:hover { + background-color: #484c56; +} + +.mstdn > span { + color: #9baec8; + font-size: 12px; + padding-left: 3px; +} +.mstdn > span:before { + content: "@"; +} diff --git a/_vendor/github.com/gohugoio/gohugoioTheme/assets/output/css/app.css b/_vendor/github.com/gohugoio/gohugoioTheme/assets/output/css/app.css index af648c759..f5e09aeb1 100644 --- a/_vendor/github.com/gohugoio/gohugoioTheme/assets/output/css/app.css +++ b/_vendor/github.com/gohugoio/gohugoioTheme/assets/output/css/app.css @@ -804,8 +804,6 @@ img { max-width: 100%; } .b--washed-red { border-color: #ffdfdf; } .b--transparent { border-color: transparent; } .b--inherit { border-color: inherit; } -.b--initial { border-color: currentColor; border-color: initial; } -.b--unset { border-color: unset; } /* BORDER RADIUS @@ -854,9 +852,6 @@ img { max-width: 100%; } border-top-right-radius: 0; border-bottom-right-radius: 0; } -.br-inherit { border-radius: inherit; } -.br-initial { border-radius: 0; border-radius: initial; } -.br-unset { border-radius: unset; } @media screen and (min-width: 30em) { .br0-ns { border-radius: 0; } .br1-ns { border-radius: .125rem; } @@ -881,9 +876,6 @@ img { max-width: 100%; } border-top-right-radius: 0; border-bottom-right-radius: 0; } - .br-inherit-ns { border-radius: inherit; } - .br-initial-ns { border-radius: 0; border-radius: initial; } - .br-unset-ns { border-radius: unset; } } @media screen and (min-width: 30em) and (max-width: 60em) { .br0-m { border-radius: 0; } @@ -909,9 +901,6 @@ img { max-width: 100%; } border-top-right-radius: 0; border-bottom-right-radius: 0; } - .br-inherit-m { border-radius: inherit; } - .br-initial-m { border-radius: 0; border-radius: initial; } - .br-unset-m { border-radius: unset; } } @media screen and (min-width: 60em) { .br0-l { border-radius: 0; } @@ -937,9 +926,6 @@ img { max-width: 100%; } border-top-right-radius: 0; border-bottom-right-radius: 0; } - .br-inherit-l { border-radius: inherit; } - .br-initial-l { border-radius: 0; border-radius: initial; } - .br-unset-l { border-radius: unset; } } /* @@ -2381,7 +2367,6 @@ img { max-width: 100%; } .washed-yellow { color: #fffceb; } .washed-red { color: #ffdfdf; } .color-inherit { color: inherit; } -/* Background colors */ .bg-black-90 { background-color: rgba(0, 0, 0, .9); } .bg-black-80 { background-color: rgba(0, 0, 0, .8); } .bg-black-70 { background-color: rgba(0, 0, 0, .7); } @@ -2401,6 +2386,7 @@ img { max-width: 100%; } .bg-white-30 { background-color: rgba(255, 255, 255, .3); } .bg-white-20 { background-color: rgba(255, 255, 255, .2); } .bg-white-10 { background-color: rgba(255, 255, 255, .1); } +/* Background colors */ .bg-black { background-color: #000; } .bg-near-black { background-color: #111; } .bg-dark-gray { background-color: #333; } @@ -4685,7 +4671,6 @@ h6:hover .header-link { .searchbox__input::-webkit-input-placeholder{color:#aaa} .searchbox__input:-ms-input-placeholder{color:#aaa} .searchbox__input::-ms-input-placeholder{color:#aaa} -.searchbox__input::-moz-placeholder{color:#aaa} .searchbox__input::placeholder{color:#aaa} .searchbox__submit{position:absolute;top:0;margin:0;border:0;border-radius:16px 0 0 16px;background-color:rgba(69, 142, 225, 0);padding:0;width:32px;height:100%;vertical-align:middle;text-align:center;font-size:inherit;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;right:inherit;left:0} .searchbox__submit:before{display:inline-block;margin-right:-4px;height:100%;vertical-align:middle;content:""} @@ -4919,14 +4904,14 @@ pre { text-decoration: none; } -.column-count-2 {-webkit-column-count: 1;-moz-column-count: 1;column-count: 1} -.column-gap-1 {-webkit-column-gap: 0;-moz-column-gap: 0;column-gap: 0} -.break-inside-avoid {-webkit-column-break-inside: auto;page-break-inside: auto;break-inside: auto} +.column-count-2 {-webkit-column-count: 1;column-count: 1} +.column-gap-1 {-webkit-column-gap: 0;column-gap: 0} +.break-inside-avoid {-webkit-column-break-inside: auto;break-inside: auto} @media screen and (min-width: 60em) { - .column-count-3-l {-webkit-column-count: 3;-moz-column-count: 3;column-count: 3} - .column-count-2-l {-webkit-column-count: 2;-moz-column-count: 2;column-count: 2} - .column-gap-1-l {-webkit-column-gap: 1;-moz-column-gap: 1;column-gap: 1} - .break-inside-avoid-l {-webkit-column-break-inside: avoid;page-break-inside: avoid;break-inside: avoid} + .column-count-3-l {-webkit-column-count: 3;column-count: 3} + .column-count-2-l {-webkit-column-count: 2;column-count: 2} + .column-gap-1-l {-webkit-column-gap: 1;column-gap: 1} + .break-inside-avoid-l {-webkit-column-break-inside: avoid;break-inside: avoid} } .prose ul, .prose ol { margin-bottom: 2em; @@ -4937,10 +4922,6 @@ pre { .prose li:hover { background-color: #eee } -.prose ::-moz-selection { - background: #0594CB; /* WebKit/Blink Browsers */ - color: white; -} .prose ::selection { background: #0594CB; /* WebKit/Blink Browsers */ color: white; @@ -5132,8 +5113,11 @@ code, .code, pre code, .highlight pre { -webkit-transition: opacity .15s ease-in; transition: opacity .15s ease-in; } -.facebook, .twitter, .instagram, .youtube { - fill: #BABABA; +.facebook, +.twitter, +.instagram, +.youtube { + fill: #bababa; } .facebook:hover { fill: #3b5998; @@ -5142,7 +5126,7 @@ code, .code, pre code, .highlight pre { fill: #55acee; } .twitter:hover { - fill: #BABABA; + fill: #bababa; } .instagram:hover { fill: #e95950; @@ -5150,6 +5134,32 @@ code, .code, pre code, .highlight pre { .youtube:hover { fill: #bb0000; } +.mstdn { + display: inline-block; + background-color: #282c37; + color: #d9e1e8; + text-decoration: none; + padding: 4px 10px 4px 30px; + border-radius: 4px; + font-size: 16px; + background-image: url("data:image/svg+xml;charset=utf8,%3Csvg%20xmlns%3D%22http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%22%20width%3D%2261.076954mm%22%20height%3D%2265.47831mm%22%20viewBox%3D%220%200%20216.4144%20232.00976%22%3E%3Cpath%20d%3D%22M211.80734%20139.0875c-3.18125%2016.36625-28.4925%2034.2775-57.5625%2037.74875-15.15875%201.80875-30.08375%203.47125-45.99875%202.74125-26.0275-1.1925-46.565-6.2125-46.565-6.2125%200%202.53375.15625%204.94625.46875%207.2025%203.38375%2025.68625%2025.47%2027.225%2046.39125%2027.9425%2021.11625.7225%2039.91875-5.20625%2039.91875-5.20625l.8675%2019.09s-14.77%207.93125-41.08125%209.39c-14.50875.7975-32.52375-.365-53.50625-5.91875C9.23234%20213.82%201.40609%20165.31125.20859%20116.09125c-.365-14.61375-.14-28.39375-.14-39.91875%200-50.33%2032.97625-65.0825%2032.97625-65.0825C49.67234%203.45375%2078.20359.2425%20107.86484%200h.72875c29.66125.2425%2058.21125%203.45375%2074.8375%2011.09%200%200%2032.975%2014.7525%2032.975%2065.0825%200%200%20.41375%2037.13375-4.59875%2062.915%22%20fill%3D%22%233088d4%22%2F%3E%3Cpath%20d%3D%22M177.50984%2080.077v60.94125h-24.14375v-59.15c0-12.46875-5.24625-18.7975-15.74-18.7975-11.6025%200-17.4175%207.5075-17.4175%2022.3525v32.37625H96.20734V85.42325c0-14.845-5.81625-22.3525-17.41875-22.3525-10.49375%200-15.74%206.32875-15.74%2018.7975v59.15H38.90484V80.077c0-12.455%203.17125-22.3525%209.54125-29.675%206.56875-7.3225%2015.17125-11.07625%2025.85-11.07625%2012.355%200%2021.71125%204.74875%2027.8975%2014.2475l6.01375%2010.08125%206.015-10.08125c6.185-9.49875%2015.54125-14.2475%2027.8975-14.2475%2010.6775%200%2019.28%203.75375%2025.85%2011.07625%206.36875%207.3225%209.54%2017.22%209.54%2029.675%22%20fill%3D%22%23fff%22%2F%3E%3C%2Fsvg%3E"); + background-size: 16px; + background-repeat: no-repeat; + background-position: top 50% left 8px; + -webkit-transition: all 0.5s; + transition: all 0.5s; +} +.mstdn:hover { + background-color: #484c56; +} +.mstdn > span { + color: #9baec8; + font-size: 12px; + padding-left: 3px; +} +.mstdn > span:before { + content: "@"; +} @media (min-width: 75em) { [data-scrolldir="down"] .sticky { diff --git a/_vendor/github.com/gohugoio/gohugoioTheme/assets/output/js/app.js b/_vendor/github.com/gohugoio/gohugoioTheme/assets/output/js/app.js index 346f209ba..a3e1801f8 100644 --- a/_vendor/github.com/gohugoio/gohugoioTheme/assets/output/js/app.js +++ b/_vendor/github.com/gohugoio/gohugoioTheme/assets/output/js/app.js @@ -1,24 +1,17 @@ -!function(t){var e={};function n(r){if(e[r])return e[r].exports;var i=e[r]={i:r,l:!1,exports:{}};return t[r].call(i.exports,i,i.exports,n),i.l=!0,i.exports}n.m=t,n.c=e,n.d=function(t,e,r){n.o(t,e)||Object.defineProperty(t,e,{enumerable:!0,get:r})},n.r=function(t){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(t,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(t,"__esModule",{value:!0})},n.t=function(t,e){if(1&e&&(t=n(t)),8&e)return t;if(4&e&&"object"==typeof t&&t&&t.__esModule)return t;var r=Object.create(null);if(n.r(r),Object.defineProperty(r,"default",{enumerable:!0,value:t}),2&e&&"string"!=typeof t)for(var i in t)n.d(r,i,function(e){return t[e]}.bind(null,i));return r},n.n=function(t){var e=t&&t.__esModule?function(){return t.default}:function(){return t};return n.d(e,"a",e),e},n.o=function(t,e){return Object.prototype.hasOwnProperty.call(t,e)},n.p="",n(n.s=1)}([function(t,e,n){!function(e,n){var r=function(t,e,n){"use strict";var r,i;if(function(){var e,n={lazyClass:"lazyload",loadedClass:"lazyloaded",loadingClass:"lazyloading",preloadClass:"lazypreload",errorClass:"lazyerror",autosizesClass:"lazyautosizes",fastLoadedClass:"ls-is-cached",iframeLoadMode:0,srcAttr:"data-src",srcsetAttr:"data-srcset",sizesAttr:"data-sizes",minSize:40,customMedia:{},init:!0,expFactor:1.5,hFac:.8,loadMode:2,loadHidden:!0,ricTimeout:0,throttleDelay:125};for(e in i=t.lazySizesConfig||t.lazysizesConfig||{},n)e in i||(i[e]=n[e])}(),!e||!e.getElementsByClassName)return{init:function(){},cfg:i,noSupport:!0};var o=e.documentElement,s=t.HTMLPictureElement,a=t.addEventListener.bind(t),u=t.setTimeout,c=t.requestAnimationFrame||u,l=t.requestIdleCallback,h=/^picture$/i,f=["load","error","lazyincluded","_lazyloaded"],p={},d=Array.prototype.forEach,g=function(t,e){return p[e]||(p[e]=new RegExp("(\\s|^)"+e+"(\\s|$)")),p[e].test(t.getAttribute("class")||"")&&p[e]},m=function(t,e){g(t,e)||t.setAttribute("class",(t.getAttribute("class")||"").trim()+" "+e)},y=function(t,e){var n;(n=g(t,e))&&t.setAttribute("class",(t.getAttribute("class")||"").replace(n," "))},v=function(t,e,n){var r=n?"addEventListener":"removeEventListener";n&&v(t,e),f.forEach((function(n){t[r](n,e)}))},b=function(t,n,i,o,s){var a=e.createEvent("Event");return i||(i={}),i.instance=r,a.initEvent(n,!o,!s),a.detail=i,t.dispatchEvent(a),a},w=function(e,n){var r;!s&&(r=t.picturefill||i.pf)?(n&&n.src&&!e.getAttribute("srcset")&&e.setAttribute("srcset",n.src),r({reevaluate:!0,elements:[e]})):n&&n.src&&(e.src=n.src)},_=function(t,e){return(getComputedStyle(t,null)||{})[e]},x=function(t,e,n){for(n=n||t.offsetWidth;n0)&&"visible"!=_(i,"overflow")&&(r=i.getBoundingClientRect(),s=z>r.left&&Fr.top-1&&H500&&o.clientWidth>500?500:370:i.expand,r._defEx=p,d=p*i.expFactor,g=i.hFac,U=null,W2&&D>2&&!e.hidden?(W=d,X=0):W=D>1&&X>1&&Q<6?p:0),f!==c&&($=innerWidth+c*g,M=innerHeight+c,l=-1*c,f=c),s=m[n].getBoundingClientRect(),(B=s.bottom)>=l&&(H=s.top)<=M&&(z=s.right)>=l*g&&(F=s.left)<=$&&(B||z||F||H)&&(i.loadHidden||Z(m[n]))&&(R&&Q<3&&!h&&(D<3||X<4)||Y(m[n],c))){if(at(m[n]),u=!0,Q>9)break}else!u&&R&&!a&&Q<4&&X<4&&D>2&&(L[0]||i.preloadAfterLoad)&&(L[0]||!h&&(B||z||F||H||"auto"!=m[n].getAttribute(i.sizesAttr)))&&(a=L[0]||m[n]);a&&!u&&at(a)}},et=function(t){var e,r=0,o=i.throttleDelay,s=i.ricTimeout,a=function(){e=!1,r=n.now(),t()},c=l&&s>49?function(){l(a,{timeout:s}),s!==i.ricTimeout&&(s=i.ricTimeout)}:C((function(){u(a)}),!0);return function(t){var i;(t=!0===t)&&(s=33),e||(e=!0,(i=o-(n.now()-r))<0&&(i=0),t||i<9?c():u(c,i))}}(tt),nt=function(t){var e=t.target;e._lazyCache?delete e._lazyCache:(G(t),m(e,i.loadedClass),y(e,i.loadingClass),v(e,it),b(e,"lazyloaded"))},rt=C(nt),it=function(t){rt({target:t.target})},ot=function(t){var e,n=t.getAttribute(i.srcsetAttr);(e=i.customMedia[t.getAttribute("data-media")||t.getAttribute("media")])&&t.setAttribute("media",e),n&&t.setAttribute("srcset",n)},st=C((function(t,e,n,r,o){var s,a,c,l,f,p;(f=b(t,"lazybeforeunveil",e)).defaultPrevented||(r&&(n?m(t,i.autosizesClass):t.setAttribute("sizes",r)),a=t.getAttribute(i.srcsetAttr),s=t.getAttribute(i.srcAttr),o&&(l=(c=t.parentNode)&&h.test(c.nodeName||"")),p=e.firesLoad||"src"in t&&(a||s||l),f={target:t},m(t,i.loadingClass),p&&(clearTimeout(P),P=u(G,2500),v(t,it,!0)),l&&d.call(c.getElementsByTagName("source"),ot),a?t.setAttribute("srcset",a):s&&!l&&(K.test(t.nodeName)?function(t,e){var n=t.getAttribute("data-load-mode")||i.iframeLoadMode;0==n?t.contentWindow.location.replace(e):1==n&&(t.src=e)}(t,s):t.src=s),o&&(a||l)&&w(t,{src:s})),t._lazyRace&&delete t._lazyRace,y(t,i.lazyClass),S((function(){var e=t.complete&&t.naturalWidth>1;p&&!e||(e&&m(t,i.fastLoadedClass),nt(f),t._lazyCache=!0,u((function(){"_lazyCache"in t&&delete t._lazyCache}),9)),"lazy"==t.loading&&Q--}),!0)})),at=function(t){if(!t._lazyRace){var e,n=V.test(t.nodeName),r=n&&(t.getAttribute(i.sizesAttr)||t.getAttribute("sizes")),o="auto"==r;(!o&&R||!n||!t.getAttribute("src")&&!t.srcset||t.complete||g(t,i.errorClass)||!g(t,i.lazyClass))&&(e=b(t,"lazyunveilread").detail,o&&T.updateElem(t,!0,t.offsetWidth),t._lazyRace=!0,Q++,st(t,e,o,r,n))}},ut=A((function(){i.loadMode=3,et()})),ct=function(){3==i.loadMode&&(i.loadMode=2),ut()},lt=function(){R||(n.now()-q<999?u(lt,999):(R=!0,i.loadMode=3,et(),a("scroll",ct,!0)))},{_:function(){q=n.now(),r.elements=e.getElementsByClassName(i.lazyClass),L=e.getElementsByClassName(i.lazyClass+" "+i.preloadClass),a("scroll",et,!0),a("resize",et,!0),a("pageshow",(function(t){if(t.persisted){var n=e.querySelectorAll("."+i.loadingClass);n.length&&n.forEach&&c((function(){n.forEach((function(t){t.complete&&at(t)}))}))}})),t.MutationObserver?new MutationObserver(et).observe(o,{childList:!0,subtree:!0,attributes:!0}):(o.addEventListener("DOMNodeInserted",et,!0),o.addEventListener("DOMAttrModified",et,!0),setInterval(et,999)),a("hashchange",et,!0),["focus","mouseover","click","load","transitionend","animationend"].forEach((function(t){e.addEventListener(t,et,!0)})),/d$|^c/.test(e.readyState)?lt():(a("load",lt),e.addEventListener("DOMContentLoaded",et),u(lt,2e4)),r.elements.length?(tt(),S._lsFlush()):et()},checkElems:et,unveil:at,_aLSL:ct}),T=(N=C((function(t,e,n,r){var i,o,s;if(t._lazysizesWidth=r,r+="px",t.setAttribute("sizes",r),h.test(e.nodeName||""))for(o=0,s=(i=e.getElementsByTagName("source")).length;o0)&&"visible"!=_(i,"overflow")&&(r=i.getBoundingClientRect(),s=z>r.left&&Fr.top-1&&H500&&o.clientWidth>500?500:370:i.expand,r._defEx=d,p=d*i.expFactor,g=i.hFac,U=null,W2&&D>2&&!e.hidden?(W=p,X=0):W=D>1&&X>1&&Q<6?d:0),f!==c&&($=innerWidth+c*g,M=innerHeight+c,l=-1*c,f=c),s=m[n].getBoundingClientRect(),(B=s.bottom)>=l&&(H=s.top)<=M&&(z=s.right)>=l*g&&(F=s.left)<=$&&(B||z||F||H)&&(i.loadHidden||Z(m[n]))&&(R&&Q<3&&!h&&(D<3||X<4)||Y(m[n],c))){if(at(m[n]),u=!0,Q>9)break}else!u&&R&&!a&&Q<4&&X<4&&D>2&&(L[0]||i.preloadAfterLoad)&&(L[0]||!h&&(B||z||F||H||"auto"!=m[n].getAttribute(i.sizesAttr)))&&(a=L[0]||m[n]);a&&!u&&at(a)}},et=function(t){var e,r=0,o=i.throttleDelay,s=i.ricTimeout,a=function(){e=!1,r=n.now(),t()},c=l&&s>49?function(){l(a,{timeout:s}),s!==i.ricTimeout&&(s=i.ricTimeout)}:C((function(){u(a)}),!0);return function(t){var i;(t=!0===t)&&(s=33),e||(e=!0,(i=o-(n.now()-r))<0&&(i=0),t||i<9?c():u(c,i))}}(tt),nt=function(t){var e=t.target;e._lazyCache?delete e._lazyCache:(G(t),m(e,i.loadedClass),y(e,i.loadingClass),v(e,it),b(e,"lazyloaded"))},rt=C(nt),it=function(t){rt({target:t.target})},ot=function(t){var e,n=t.getAttribute(i.srcsetAttr);(e=i.customMedia[t.getAttribute("data-media")||t.getAttribute("media")])&&t.setAttribute("media",e),n&&t.setAttribute("srcset",n)},st=C((function(t,e,n,r,o){var s,a,c,l,f,d;(f=b(t,"lazybeforeunveil",e)).defaultPrevented||(r&&(n?m(t,i.autosizesClass):t.setAttribute("sizes",r)),a=t.getAttribute(i.srcsetAttr),s=t.getAttribute(i.srcAttr),o&&(l=(c=t.parentNode)&&h.test(c.nodeName||"")),d=e.firesLoad||"src"in t&&(a||s||l),f={target:t},m(t,i.loadingClass),d&&(clearTimeout(P),P=u(G,2500),v(t,it,!0)),l&&p.call(c.getElementsByTagName("source"),ot),a?t.setAttribute("srcset",a):s&&!l&&(K.test(t.nodeName)?function(t,e){var n=t.getAttribute("data-load-mode")||i.iframeLoadMode;0==n?t.contentWindow.location.replace(e):1==n&&(t.src=e)}(t,s):t.src=s),o&&(a||l)&&w(t,{src:s})),t._lazyRace&&delete t._lazyRace,y(t,i.lazyClass),S((function(){var e=t.complete&&t.naturalWidth>1;d&&!e||(e&&m(t,i.fastLoadedClass),nt(f),t._lazyCache=!0,u((function(){"_lazyCache"in t&&delete t._lazyCache}),9)),"lazy"==t.loading&&Q--}),!0)})),at=function(t){if(!t._lazyRace){var e,n=V.test(t.nodeName),r=n&&(t.getAttribute(i.sizesAttr)||t.getAttribute("sizes")),o="auto"==r;(!o&&R||!n||!t.getAttribute("src")&&!t.srcset||t.complete||g(t,i.errorClass)||!g(t,i.lazyClass))&&(e=b(t,"lazyunveilread").detail,o&&T.updateElem(t,!0,t.offsetWidth),t._lazyRace=!0,Q++,st(t,e,o,r,n))}},ut=A((function(){i.loadMode=3,et()})),ct=function(){3==i.loadMode&&(i.loadMode=2),ut()},lt=function(){R||(n.now()-q<999?u(lt,999):(R=!0,i.loadMode=3,et(),a("scroll",ct,!0)))},{_:function(){q=n.now(),r.elements=e.getElementsByClassName(i.lazyClass),L=e.getElementsByClassName(i.lazyClass+" "+i.preloadClass),a("scroll",et,!0),a("resize",et,!0),a("pageshow",(function(t){if(t.persisted){var n=e.querySelectorAll("."+i.loadingClass);n.length&&n.forEach&&c((function(){n.forEach((function(t){t.complete&&at(t)}))}))}})),t.MutationObserver?new MutationObserver(et).observe(o,{childList:!0,subtree:!0,attributes:!0}):(o.addEventListener("DOMNodeInserted",et,!0),o.addEventListener("DOMAttrModified",et,!0),setInterval(et,999)),a("hashchange",et,!0),["focus","mouseover","click","load","transitionend","animationend"].forEach((function(t){e.addEventListener(t,et,!0)})),/d$|^c/.test(e.readyState)?lt():(a("load",lt),e.addEventListener("DOMContentLoaded",et),u(lt,2e4)),r.elements.length?(tt(),S._lsFlush()):et()},checkElems:et,unveil:at,_aLSL:ct}),T=(N=C((function(t,e,n,r){var i,o,s;if(t._lazysizesWidth=r,r+="px",t.setAttribute("sizes",r),h.test(e.nodeName||""))for(o=0,s=(i=e.getElementsByTagName("source")).length;o1&&void 0!==arguments[1]?arguments[1]:{container:document.body},n="";return"string"==typeof t?n=h(t,e):t instanceof HTMLInputElement&&!["text","search","url","tel","password"].includes(null==t?void 0:t.type)?n=h(t.value,e):(n=u()(t),c("copy")),n};function p(t){return(p="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t})(t)}var d=function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:{},e=t.action,n=void 0===e?"copy":e,r=t.container,i=t.target,o=t.text;if("copy"!==n&&"cut"!==n)throw new Error('Invalid "action" value, use either "copy" or "cut"');if(void 0!==i){if(!i||"object"!==p(i)||1!==i.nodeType)throw new Error('Invalid "target" value, use a valid Element');if("copy"===n&&i.hasAttribute("disabled"))throw new Error('Invalid "target" attribute. Please use "readonly" instead of "disabled" attribute');if("cut"===n&&(i.hasAttribute("readonly")||i.hasAttribute("disabled")))throw new Error('Invalid "target" attribute. You can\'t cut text from elements with "readonly" or "disabled" attributes')}return o?f(o,{container:r}):i?"cut"===n?l(i):f(i,{container:r}):void 0};function g(t){return(g="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t})(t)}function m(t,e){for(var n=0;n1&&void 0!==arguments[1]?arguments[1]:{container:document.body};return f(t,e)}},{key:"cut",value:function(t){return l(t)}},{key:"isSupported",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:["copy","cut"],e="string"==typeof t?[t]:t,n=!!document.queryCommandSupported;return e.forEach((function(t){n=n&&!!document.queryCommandSupported(t)})),n}}],(n=[{key:"resolveOptions",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:{};this.action="function"==typeof t.action?t.action:this.defaultAction,this.target="function"==typeof t.target?t.target:this.defaultTarget,this.text="function"==typeof t.text?t.text:this.defaultText,this.container="object"===g(t.container)?t.container:document.body}},{key:"listenClick",value:function(t){var e=this;this.listener=s()(t,"click",(function(t){return e.onClick(t)}))}},{key:"onClick",value:function(t){var e=t.delegateTarget||t.currentTarget,n=this.action(e)||"copy",r=d({action:n,container:this.container,target:this.target(e),text:this.text(e)});this.emit(r?"success":"error",{action:n,text:r,trigger:e,clearSelection:function(){e&&e.focus(),window.getSelection().removeAllRanges()}})}},{key:"defaultAction",value:function(t){return _("action",t)}},{key:"defaultTarget",value:function(t){var e=_("target",t);if(e)return document.querySelector(e)}},{key:"defaultText",value:function(t){return _("text",t)}},{key:"destroy",value:function(){this.listener.destroy()}}])&&m(e.prototype,n),r&&m(e,r),o}(i())},828:function(t){if("undefined"!=typeof Element&&!Element.prototype.matches){var e=Element.prototype;e.matches=e.matchesSelector||e.mozMatchesSelector||e.msMatchesSelector||e.oMatchesSelector||e.webkitMatchesSelector}t.exports=function(t,e){for(;t&&9!==t.nodeType;){if("function"==typeof t.matches&&t.matches(e))return t;t=t.parentNode}}},438:function(t,e,n){var r=n(828);function i(t,e,n,r,i){var s=o.apply(this,arguments);return t.addEventListener(n,s,i),{destroy:function(){t.removeEventListener(n,s,i)}}}function o(t,e,n,i){return function(n){n.delegateTarget=r(n.target,e),n.delegateTarget&&i.call(t,n)}}t.exports=function(t,e,n,r,o){return"function"==typeof t.addEventListener?i.apply(null,arguments):"function"==typeof n?i.bind(null,document).apply(null,arguments):("string"==typeof t&&(t=document.querySelectorAll(t)),Array.prototype.map.call(t,(function(t){return i(t,e,n,r,o)})))}},879:function(t,e){e.node=function(t){return void 0!==t&&t instanceof HTMLElement&&1===t.nodeType},e.nodeList=function(t){var n=Object.prototype.toString.call(t);return void 0!==t&&("[object NodeList]"===n||"[object HTMLCollection]"===n)&&"length"in t&&(0===t.length||e.node(t[0]))},e.string=function(t){return"string"==typeof t||t instanceof String},e.fn=function(t){return"[object Function]"===Object.prototype.toString.call(t)}},370:function(t,e,n){var r=n(879),i=n(438);t.exports=function(t,e,n){if(!t&&!e&&!n)throw new Error("Missing required arguments");if(!r.string(e))throw new TypeError("Second argument must be a String");if(!r.fn(n))throw new TypeError("Third argument must be a Function");if(r.node(t))return function(t,e,n){return t.addEventListener(e,n),{destroy:function(){t.removeEventListener(e,n)}}}(t,e,n);if(r.nodeList(t))return function(t,e,n){return Array.prototype.forEach.call(t,(function(t){t.addEventListener(e,n)})),{destroy:function(){Array.prototype.forEach.call(t,(function(t){t.removeEventListener(e,n)}))}}}(t,e,n);if(r.string(t))return function(t,e,n){return i(document.body,t,e,n)}(t,e,n);throw new TypeError("First argument must be a String, HTMLElement, HTMLCollection, or NodeList")}},817:function(t){t.exports=function(t){var e;if("SELECT"===t.nodeName)t.focus(),e=t.value;else if("INPUT"===t.nodeName||"TEXTAREA"===t.nodeName){var n=t.hasAttribute("readonly");n||t.setAttribute("readonly",""),t.select(),t.setSelectionRange(0,t.value.length),n||t.removeAttribute("readonly"),e=t.value}else{t.hasAttribute("contenteditable")&&t.focus();var r=window.getSelection(),i=document.createRange();i.selectNodeContents(t),r.removeAllRanges(),r.addRange(i),e=r.toString()}return e}},279:function(t){function e(){}e.prototype={on:function(t,e,n){var r=this.e||(this.e={});return(r[t]||(r[t]=[])).push({fn:e,ctx:n}),this},once:function(t,e,n){var r=this;function i(){r.off(t,i),e.apply(n,arguments)}return i._=e,this.on(t,i,n)},emit:function(t){for(var e=[].slice.call(arguments,1),n=((this.e||(this.e={}))[t]||[]).slice(),r=0,i=n.length;r";var r=document.createElement("div");r.appendChild(document.createTextNode(e)),n=n||"";var i=document.createElement("div");i.appendChild(document.createTextNode(n));var s=document.createElement("div");return s.appendChild(document.createTextNode(t)),s.innerHTML.replace(RegExp(o(r.innerHTML),"g"),e).replace(RegExp(o(i.innerHTML),"g"),n)}}},function(t,e,n){"use strict";t.exports={element:null}},function(t,e){var n=Object.prototype.hasOwnProperty,r=Object.prototype.toString;t.exports=function(t,e,i){if("[object Function]"!==r.call(e))throw new TypeError("iterator must be a function");var o=t.length;if(o===+o)for(var s=0;s was loaded but did not call our provided callback"),JSONPScriptError:o("JSONPScriptError","` → `` +* `` → `` diff --git a/content/en/functions/safe/JSStr.md b/content/en/functions/safe/JSStr.md new file mode 100644 index 000000000..790de3a73 --- /dev/null +++ b/content/en/functions/safe/JSStr.md @@ -0,0 +1,61 @@ +--- +title: safe.JSStr +linkTitle: safeJSStr +description: Declares the provided string as a known safe JavaScript string. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [safeJSStr] + returnType: template.JSStr + signatures: [safe.JSStr INPUT] +relatedFunctions: + - safe.CSS + - safe.HTML + - safe.HTMLAttr + - safe.JS + - safe.JSStr + - safe.URL +aliases: [/functions/safejsstr] +--- + +Encapsulates a sequence of characters meant to be embedded between quotes in a JavaScript expression. Use of this type presents a security risk: the encapsulated content should come from a trusted source, as it will be included verbatim in the template output. + +Without declaring a variable to be a safe JavaScript string: + +```go-html-template +{{ $title := "Lilo & Stitch" }} + +``` + +Rendered: + + +```html + +``` + +To avoid escaping by Go's [html/template] package: + +```go-html-template +{{ $title := "Lilo & Stitch" }} + +``` + +Rendered: + +```html + +``` + +[html/template]: https://pkg.go.dev/html/template diff --git a/content/en/functions/safe/URL.md b/content/en/functions/safe/URL.md new file mode 100644 index 000000000..edc62ff9d --- /dev/null +++ b/content/en/functions/safe/URL.md @@ -0,0 +1,75 @@ +--- +title: safe.URL +linkTitle: safeURL +description: Declares the provided string as a safe URL or URL substring. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [safeURL] + returnType: template.URL + signatures: [safe.URL INPUT] +relatedFunctions: + - safe.CSS + - safe.HTML + - safe.HTMLAttr + - safe.JS + - safe.JSStr + - safe.URL +aliases: [/functions/safeurl] +--- + +`safeURL` declares the provided string as a "safe" URL or URL substring (see [RFC 3986]). A URL like `javascript:checkThatFormNotEditedBeforeLeavingPage()` from a trusted source should go in the page, but by default dynamic `javascript:` URLs are filtered out since they are a frequently exploited injection vector. + +Without `safeURL`, only the URI schemes `http:`, `https:` and `mailto:` are considered safe by Go templates. If any other URI schemes (e.g., `irc:` and `javascript:`) are detected, the whole URL will be replaced with `#ZgotmplZ`. This is to "defang" any potential attack in the URL by rendering it useless. + +The following examples use a [site `hugo.toml`][configuration] with the following [menu entry][menus]: + +{{< code-toggle file="hugo" copy=false >}} +[[menu.main]] +name = "IRC: #golang at freenode" +url = "irc://irc.freenode.net/#golang" +{{< /code-toggle >}} + +The following is an example of a sidebar partial that may be used in conjunction with the preceding front matter example: + +{{< code file="layouts/partials/bad-url-sidebar-menu.html" copy=false >}} + +
    + {{ range .Site.Menus.main }} +
  • {{ .Name }}
  • + {{ end }} +
+{{< /code >}} + +This partial would produce the following HTML output: + +```html + + +``` + +The odd output can be remedied by adding ` | safeURL` to our `.URL` page variable: + +{{< code file="layouts/partials/correct-url-sidebar-menu.html" copy=false >}} + + +{{< /code >}} + +With the `.URL` page variable piped through `safeURL`, we get the desired output: + +```html + +``` + +[configuration]: /getting-started/configuration/ +[menus]: /content-management/menus/ +[RFC 3986]: https://tools.ietf.org/html/rfc3986 diff --git a/content/en/functions/safeCSS.md b/content/en/functions/safeCSS.md deleted file mode 100644 index 93595286c..000000000 --- a/content/en/functions/safeCSS.md +++ /dev/null @@ -1,27 +0,0 @@ ---- -title: safeCSS -description: Declares the provided string as a known "safe" CSS string. -categories: [functions] -menu: - docs: - parent: functions -keywords: [style,css,strings] -signature: ["safeCSS INPUT"] -relatedfuncs: [safeHTML,safeHTMLAttr,] ---- - -In this context, *safe* means CSS content that matches any of the following: - -1. The CSS3 stylesheet production, such as `p { color: purple }`. -2. The CSS3 rule production, such as `a[href=~"https:"].foo#bar`. -3. CSS3 declaration productions, such as `color: red; margin: 2px`. -4. The CSS3 value production, such as `rgba(0, 0, 255, 127)`. - -Example: Given `style = "color: red;"` defined in the front matter of your `.md` file: - -* `

…

` → `

…

`
-* `

…

` → `

…

`
- -{{% note %}} -"ZgotmplZ" is a special value that indicates that unsafe content reached a CSS or URL context. -{{% /note %}} diff --git a/content/en/functions/safeHTML.md b/content/en/functions/safeHTML.md deleted file mode 100644 index 4e74b44d4..000000000 --- a/content/en/functions/safeHTML.md +++ /dev/null @@ -1,33 +0,0 @@ ---- -title: safeHTML -description: Declares a provided string as a "safe" HTML document to avoid escaping by Go templates. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["safeHTML INPUT"] -relatedfuncs: [] ---- - -It should not be used for HTML from a third-party, or HTML with unclosed tags or comments. - -Given a site-wide [`hugo.toml`][config] with the following `copyright` value: - -{{< code-toggle file="hugo" >}} -copyright = "© 2015 Jane Doe. Some rights reserved." -{{< /code-toggle >}} - -`{{ .Site.Copyright | safeHTML }}` in a template would then output: - -```html -© 2015 Jane Doe. Some rights reserved. -``` - -However, without the `safeHTML` function, html/template assumes `.Site.Copyright` to be unsafe and therefore escapes all HTML tags and renders the whole string as plain text: - -```html -

© 2015 Jane Doe. <a href="https://creativecommons.org/licenses by/4.0/">Some rights reserved</a>.

-``` - -[config]: /getting-started/configuration/ diff --git a/content/en/functions/safeHTMLAttr.md b/content/en/functions/safeHTMLAttr.md deleted file mode 100644 index bced1ba10..000000000 --- a/content/en/functions/safeHTMLAttr.md +++ /dev/null @@ -1,49 +0,0 @@ ---- -title: safeHTMLAttr -description: Declares the provided string as a safe HTML attribute. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["safeHTMLAttr INPUT"] -relatedfuncs: [] ---- - -Given a site configuration that contains this menu entry: - -{{< code-toggle file="hugo" >}} -[[menu.main]] - name = "IRC" - url = "irc://irc.freenode.net/#golang" -{{< /code-toggle >}} - -Attempting to use the `url` value directly in an attribute: - -```go-html-template -{{ range site.Menus.main }} - {{ .Name }} -{{ end }} -``` - -Will produce: - -```html -IRC -``` - -`ZgotmplZ` is a special value, inserted by Go's [template/html] package, that indicates that unsafe content reached a CSS or URL context. - -To indicate that the HTML attribute is safe: - -```go-html-template -{{ range site.Menus.main }} - {{ .Name }} -{{ end }} -``` - -{{% note %}} -As demonstrated above, you must pass the HTML attribute name _and_ value through the function. Applying `safeHTMLAttr` to the attribute value has no effect. -{{% /note %}} - -[template/html]: https://pkg.go.dev/html/template diff --git a/content/en/functions/safeJS.md b/content/en/functions/safeJS.md deleted file mode 100644 index 48c2c363b..000000000 --- a/content/en/functions/safeJS.md +++ /dev/null @@ -1,20 +0,0 @@ ---- -title: safeJS -description: Declares the provided string as a known safe JavaScript string. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["safeJS INPUT"] -relatedfuncs: [] ---- - -In this context, *safe* means the string encapsulates a known safe EcmaScript5 Expression (e.g., `(x + y * z())`). - -Template authors are responsible for ensuring that typed expressions do not break the intended precedence and that there is no statement/expression ambiguity as when passing an expression like `{ foo:bar() }\n['foo']()`, which is both a valid expression and a valid program with a very different meaning. - -Example: Given `hash = "619c16f"` defined in the front matter of your `.md` file: - -* `` → `` -* `` → `` diff --git a/content/en/functions/safeURL.md b/content/en/functions/safeURL.md deleted file mode 100644 index b21de4953..000000000 --- a/content/en/functions/safeURL.md +++ /dev/null @@ -1,64 +0,0 @@ ---- -title: safeURL -description: Declares the provided string as a safe URL or URL substring. -keywords: [strings,urls] -categories: [functions] -menu: - docs: - parent: functions -signature: ["safeURL INPUT"] -relatedfuncs: [] ---- - -`safeURL` declares the provided string as a "safe" URL or URL substring (see [RFC 3986]). A URL like `javascript:checkThatFormNotEditedBeforeLeavingPage()` from a trusted source should go in the page, but by default dynamic `javascript:` URLs are filtered out since they are a frequently exploited injection vector. - -Without `safeURL`, only the URI schemes `http:`, `https:` and `mailto:` are considered safe by Go templates. If any other URI schemes (e.g., `irc:` and `javascript:`) are detected, the whole URL will be replaced with `#ZgotmplZ`. This is to "defang" any potential attack in the URL by rendering it useless. - -The following examples use a [site `hugo.toml`][configuration] with the following [menu entry][menus]: - -{{< code-toggle file="hugo" copy=false >}} -[[menu.main]] -name = "IRC: #golang at freenode" -url = "irc://irc.freenode.net/#golang" -{{< /code-toggle >}} - -The following is an example of a sidebar partial that may be used in conjunction with the preceding front matter example: - -{{< code file="layouts/partials/bad-url-sidebar-menu.html" copy=false >}} - -
    - {{ range .Site.Menus.main }} -
  • {{ .Name }}
  • - {{ end }} -
-{{< /code >}} - -This partial would produce the following HTML output: - -```html - - -``` - -The odd output can be remedied by adding ` | safeURL` to our `.URL` page variable: - -{{< code file="layouts/partials/correct-url-sidebar-menu.html" copy=false >}} - - -{{< /code >}} - -With the `.URL` page variable piped through `safeURL`, we get the desired output: - -```html - -``` - -[configuration]: /getting-started/configuration/ -[menus]: /content-management/menus/ -[RFC 3986]: https://tools.ietf.org/html/rfc3986 diff --git a/content/en/functions/scratch.md b/content/en/functions/scratch.md deleted file mode 100644 index 16e502b84..000000000 --- a/content/en/functions/scratch.md +++ /dev/null @@ -1,147 +0,0 @@ ---- -title: .Scratch -description: Acts as a "scratchpad" to store and manipulate data. -keywords: [iteration] -categories: [functions] -menu: - docs: - parent: functions -toc: -signature: [] -relatedfuncs: [] -aliases: [/extras/scratch/,/doc/scratch/] ---- - -Scratch is a Hugo feature designed to conveniently manipulate data in a Go Template world. It is either a Page or Shortcode method for which the resulting data will be attached to the given context, or it can live as a unique instance stored in a variable. - -{{% note %}} -Note that Scratch was initially created as a workaround for a [Go template scoping limitation](https://github.com/golang/go/issues/10608) that affected Hugo versions prior to 0.48. For a detailed analysis of `.Scratch` and contextual use cases, see [this blog post](https://regisphilibert.com/blog/2017/04/hugo-scratch-explained-variable/). -{{% /note %}} - -### Contexted `.Scratch` vs. local `newScratch` - -Since Hugo 0.43, there are two different ways of using Scratch: - -#### The Page's `.Scratch` - -`.Scratch` is available as a Page method or a Shortcode method and attaches the "scratched" data to the given page. Either a Page or a Shortcode context is required to use `.Scratch`. - -```go-html-template -{{ .Scratch.Set "greeting" "bonjour" }} -{{ range .Pages }} - {{ .Scratch.Set "greeting" (print "bonjour" .Title) }} -{{ end }} -``` - -#### The local `newScratch` - -A Scratch instance can also be assigned to any variable using the `newScratch` function. In this case, no Page or Shortcode context is required and the scope of the scratch is only local. The methods detailed below are available from the variable the Scratch instance was assigned to. - -```go-html-template -{{ $data := newScratch }} -{{ $data.Set "greeting" "hola" }} -``` - -### Methods - -A Scratch has the following methods: - -{{% note %}} -Note that the following examples assume a [local Scratch instance](#the-local-newscratch) has been stored in `$scratch`. -{{% /note %}} - -#### .Set - -Set the value of a given key. - -```go-html-template -{{ $scratch.Set "greeting" "Hello" }} -``` - -#### .Get - -Get the value of a given key. - -```go-html-template -{{ $scratch.Set "greeting" "Hello" }} ----- -{{ $scratch.Get "greeting" }} > Hello -``` - -#### .Add - -Add a given value to existing value(s) of the given key. - -For single values, `Add` accepts values that support Go's `+` operator. If the first `Add` for a key is an array or slice, the following adds will be [appended](/functions/append/) to that list. - -```go-html-template -{{ $scratch.Add "greetings" "Hello" }} -{{ $scratch.Add "greetings" "Welcome" }} ----- -{{ $scratch.Get "greetings" }} > HelloWelcome -``` - -```go-html-template -{{ $scratch.Add "total" 3 }} -{{ $scratch.Add "total" 7 }} ----- -{{ $scratch.Get "total" }} > 10 -``` - -```go-html-template -{{ $scratch.Add "greetings" (slice "Hello") }} -{{ $scratch.Add "greetings" (slice "Welcome" "Cheers") }} ----- -{{ $scratch.Get "greetings" }} > []interface {}{"Hello", "Welcome", "Cheers"} -``` - -#### .SetInMap - -Takes a `key`, `mapKey` and `value` and adds a map of `mapKey` and `value` to the given `key`. - -```go-html-template -{{ $scratch.SetInMap "greetings" "english" "Hello" }} -{{ $scratch.SetInMap "greetings" "french" "Bonjour" }} ----- -{{ $scratch.Get "greetings" }} > map[french:Bonjour english:Hello] -``` - -#### .DeleteInMap -Takes a `key` and `mapKey` and removes the map of `mapKey` from the given `key`. - -```go-html-template -{{ .Scratch.SetInMap "greetings" "english" "Hello" }} -{{ .Scratch.SetInMap "greetings" "french" "Bonjour" }} ----- -{{ .Scratch.DeleteInMap "greetings" "english" }} ----- -{{ .Scratch.Get "greetings" }} > map[french:Bonjour] -``` - -#### .GetSortedMapValues - -Return an array of values from `key` sorted by `mapKey`. - -```go-html-template -{{ $scratch.SetInMap "greetings" "english" "Hello" }} -{{ $scratch.SetInMap "greetings" "french" "Bonjour" }} ----- -{{ $scratch.GetSortedMapValues "greetings" }} > [Hello Bonjour] -``` - -#### .Delete - -Remove the given key. - -```go-html-template -{{ $scratch.Set "greeting" "Hello" }} ----- -{{ $scratch.Delete "greeting" }} -``` - -#### .Values - -Return the raw backing map. Note that you should only use this method on the locally scoped Scratch instances you obtain via [`newScratch`](#the-local-newscratch), not `.Page.Scratch` etc., as that will lead to concurrency issues. - - -[pagevars]: /variables/page/ diff --git a/content/en/functions/seq.md b/content/en/functions/seq.md deleted file mode 100644 index 75edf5d2d..000000000 --- a/content/en/functions/seq.md +++ /dev/null @@ -1,28 +0,0 @@ ---- -title: seq -description: Returns a slice of integers. -categories: [functions] -menu: - docs: - parent: functions -keywords: [] -signature: ["seq LAST", "seq FIRST LAST", "seq FIRST INCREMENT LAST"] -relatedfuncs: [] ---- - -```go-html-template -{{ seq 2 }} → [1 2] -{{ seq 0 2 }} → [0 1 2] -{{ seq -2 2 }} → [-2 -1 0 1 2] -{{ seq -2 2 2 }} → [-2 0 2] -``` - -Iterate over a sequence of integers: - -```go-html-template -{{ $product := 1 }} -{{ range seq 4 }} - {{ $product = mul $product . }} -{{ end }} -{{ $product }} → 24 -``` diff --git a/content/en/functions/sha.md b/content/en/functions/sha.md deleted file mode 100644 index 1f6cf8da0..000000000 --- a/content/en/functions/sha.md +++ /dev/null @@ -1,26 +0,0 @@ ---- -title: sha -description: Hashes the given input and returns either an SHA1 or SHA256 checksum. -categories: [functions] -menu: - docs: - parent: functions -keywords: [sha,checksum] -signature: ["sha1 INPUT", "sha256 INPUT"] -relatedfuncs: [md5] -aliases: [sha1, sha256] ---- - -`sha1` hashes the given input and returns its SHA1 checksum. - -```go-html-template -{{ sha1 "Hello world, gophers!" }} - -``` - -`sha256` hashes the given input and returns its SHA256 checksum. - -```go-html-template -{{ sha256 "Hello world, gophers!" }} - -``` diff --git a/content/en/functions/shuffle.md b/content/en/functions/shuffle.md deleted file mode 100644 index 4de66da28..000000000 --- a/content/en/functions/shuffle.md +++ /dev/null @@ -1,19 +0,0 @@ ---- -title: shuffle -description: Returns a random permutation of a given array or slice. -keywords: [ordering] -categories: [functions] -menu: - docs: - parent: functions -signature: ["shuffle COLLECTION"] -relatedfuncs: [seq] ---- - - -```go-html-template -{{ shuffle (seq 1 2 3) }} → [3 1 2] -{{ shuffle (slice "a" "b" "c") }} → [b a c] -``` - -The result will vary from one build to the next. diff --git a/content/en/functions/singularize.md b/content/en/functions/singularize.md deleted file mode 100644 index 4e56684b9..000000000 --- a/content/en/functions/singularize.md +++ /dev/null @@ -1,15 +0,0 @@ ---- -title: singularize -description: Converts a word according to a set of common English singularization rules. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings,singular] -signature: ["singularize INPUT"] -relatedfuncs: [] ---- - -`{{ "cats" | singularize }}` → "cat" - -See also the `.Data.Singular` [taxonomy variable](/variables/taxonomy/) for singularizing taxonomy names. diff --git a/content/en/functions/site.md b/content/en/functions/site.md deleted file mode 100644 index b408f7141..000000000 --- a/content/en/functions/site.md +++ /dev/null @@ -1,14 +0,0 @@ ---- -title: site -description: The `site` function provides global access to the same data as the `.Site` page method. -keywords: [] -categories: [functions] -menu: - docs: - parent: functions -toc: -signature: ["site"] -relatedfuncs: ["hugo"] ---- - -`site` is a global function which returns the same data as the `.Site` page method. See: [Site Variables](/variables/site). diff --git a/content/en/functions/site/index.md b/content/en/functions/site/index.md new file mode 100644 index 000000000..3341bff98 --- /dev/null +++ b/content/en/functions/site/index.md @@ -0,0 +1,35 @@ +--- +title: site +description: Provides global access to the .Site object. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: + signatures: [site] +relatedFunctions: + - hugo + - page + - site +aliases: [/functions/site] +--- + +At the top level of a template that receives the `Site` object in context, these are equivalent: + +```go-html-template +{{ .Site.Params.foo }} +{{ site.Params.foo }} +``` + +When the `Site` object is not in context, use the global `site` function: + +```go-html-template +{{ site.Params.foo }} +``` + +{{% note %}} +To simplify your templates, use the global `site` function regardless of whether the `Site` object is in context. +{{% /note %}} diff --git a/content/en/functions/slice.md b/content/en/functions/slice.md deleted file mode 100644 index d2ef62861..000000000 --- a/content/en/functions/slice.md +++ /dev/null @@ -1,23 +0,0 @@ ---- -title: slice -description: Creates a slice (array) of all passed arguments. -categories: [functions] -menu: - docs: - parent: functions -keywords: [slice, array, interface] -signature: ["slice ITEM..."] -relatedfuncs: [] ---- - -One use case is the concatenation of elements in combination with the [`delimit` function]: - -{{< code file="slice.html" >}} -{{ $sliceOfStrings := slice "foo" "bar" "buzz" }} - -{{ delimit ($sliceOfStrings) ", " }} - -{{< /code >}} - - -[`delimit` function]: /functions/delimit/ diff --git a/content/en/functions/slicestr.md b/content/en/functions/slicestr.md deleted file mode 100644 index bbdf95696..000000000 --- a/content/en/functions/slicestr.md +++ /dev/null @@ -1,19 +0,0 @@ ---- -title: slicestr -description: Creates a slice of a half-open range, including start and end indices. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: - - "slicestr STRING START [END]" - - "strings.SliceString STRING START [END]" -relatedfuncs: [] ---- - -For example, 1 and 4 creates a slice including elements 1 through 3. -The `end` index can be omitted; it defaults to the string's length. - -* `{{ slicestr "BatMan" 3 }}` → "Man" -* `{{ slicestr "BatMan" 0 3 }}` → "Bat" diff --git a/content/en/functions/sort.md b/content/en/functions/sort.md deleted file mode 100644 index aa15f5cd6..000000000 --- a/content/en/functions/sort.md +++ /dev/null @@ -1,126 +0,0 @@ ---- -title: sort -description: Sorts slices, maps, and page collections. -categories: [functions] -signature: ["sort COLLECTION [KEY] [ORDER]"] -menu: - docs: - parent: functions -keywords: [ordering,sorting,lists] -toc: true ---- - -The `KEY` is optional when sorting slices in ascending order, otherwise it is required. When sorting slices, use the literal `value` in place of the `KEY`. See examples below. - -The `ORDER` may be either `asc` (ascending) or `desc` (descending). The default sort order is ascending. - -## Sort a slice - -The examples below assume this site configuration: - -{{< code-toggle file="hugo" copy=false >}} -[params] -grades = ['b','a','c'] -{{< /code-toggle >}} - -### Ascending order {#slice-ascending-order} - -Sort slice elements in ascending order using either of these constructs: - -{{< code file="layouts/_default/single.html" copy=false >}} -{{ sort site.Params.grades }} → [a b c] -{{ sort site.Params.grades "value" "asc" }} → [a b c] -{{< /code >}} - -In the examples above, `value` is the `KEY` representing the value of the slice element. - -### Descending order {#slice-descending-order} - -Sort slice elements in descending order: - -{{< code file="layouts/_default/single.html" copy=false >}} -{{ sort site.Params.grades "value" "desc" }} → [c b a] -{{< /code >}} - -In the example above, `value` is the `KEY` representing the value of the slice element. - -## Sort a map - -The examples below assume this site configuration: - -{{< code-toggle file="hugo" copy=false >}} -[params.authors.a] -firstName = "Marius" -lastName = "Pontmercy" -[params.authors.b] -firstName = "Victor" -lastName = "Hugo" -[params.authors.c] -firstName = "Jean" -lastName = "Valjean" -{{< /code-toggle >}} - -{{% note %}} -When sorting maps, the `KEY` argument must be lowercase. -{{% /note %}} - -### Ascending order {#map-ascending-order} - -Sort map objects in ascending order using either of these constructs: - -{{< code file="layouts/_default/single.html" copy=false >}} -{{ range sort site.Params.authors "firstname" }} - {{ .firstName }} -{{ end }} - -{{ range sort site.Params.authors "firstname" "asc" }} - {{ .firstName }} -{{ end }} -{{< /code >}} - -These produce: - -```text -Jean Marius Victor -``` - -### Descending order {#map-descending-order} - -Sort map objects in descending order: - -{{< code file="layouts/_default/single.html" copy=false >}} -{{ range sort site.Params.authors "firstname" "desc" }} - {{ .firstName }} -{{ end }} -{{< /code >}} - -This produces: - -```text -Victor Marius Jean -``` - -## Sort a page collection - -Although you can use the `sort` function to sort a page collection, Hugo provides [built-in methods for sorting page collections] by: - -- weight -- linktitle -- title -- front matter parameter -- date -- expiration date -- last modified date -- publish date -- length - -In this contrived example, sort the site's regular pages by `.Type` in descending order: - -{{< code file="layouts/_default/home.html" copy=false >}} -{{ range sort site.RegularPages "Type" "desc" }} -

{{ .Title }}

-{{ end }} -{{< /code >}} - - -[built-in methods for sorting page collections]: /templates/lists/#order-content diff --git a/content/en/functions/split.md b/content/en/functions/split.md deleted file mode 100644 index d2f3cc8b3..000000000 --- a/content/en/functions/split.md +++ /dev/null @@ -1,23 +0,0 @@ ---- -title: split -description: Returns a slice of strings by splitting STRING by DELIM. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["split STRING DELIM"] -relatedfuncs: [] ---- - -Examples: - -```go-html-template -{{ split "tag1,tag2,tag3" "," }} → ["tag1", "tag2", "tag3"] -{{ split "abc" "" }} → ["a", "b", "c"] -``` - - -{{% note %}} -`split` essentially does the opposite of [delimit](/functions/delimit). While `split` creates a slice from a string, `delimit` creates a string from a slice. -{{% /note %}} diff --git a/content/en/functions/store.md b/content/en/functions/store.md deleted file mode 100644 index d57194d80..000000000 --- a/content/en/functions/store.md +++ /dev/null @@ -1,105 +0,0 @@ ---- -title: .Store -description: Returns a Scratch that is not reset on server rebuilds. -categories: [functions] -menu: - docs: - parent: functions -keywords: [scratch] -signature: [] ---- - -The `.Store` method on `.Page` returns a [Scratch] to store and manipulate data. In contrast to the `.Scratch` method, this Scratch is not reset on server rebuilds. - -[Scratch]: /functions/scratch/ - -### Methods - -#### .Set - -Sets the value of a given key. - -```go-html-template -{{ .Store.Set "greeting" "Hello" }} -``` - -#### .Get - -Gets the value of a given key. - -```go-html-template -{{ .Store.Set "greeting" "Hello" }} - -{{ .Store.Get "greeting" }} → Hello -``` - -#### .Add - -Adds a given value to existing value(s) of the given key. - -For single values, `Add` accepts values that support Go's `+` operator. If the first `Add` for a key is an array or slice, the following adds will be appended to that list. - -```go-html-template -{{ .Store.Add "greetings" "Hello" }} -{{ .Store.Add "greetings" "Welcome" }} - -{{ .Store.Get "greetings" }} → HelloWelcome -``` - -```go-html-template -{{ .Store.Add "total" 3 }} -{{ .Store.Add "total" 7 }} - -{{ .Store.Get "total" }} → 10 -``` - -```go-html-template -{{ .Store.Add "greetings" (slice "Hello") }} -{{ .Store.Add "greetings" (slice "Welcome" "Cheers") }} - -{{ .Store.Get "greetings" }} → []interface {}{"Hello", "Welcome", "Cheers"} -``` - -#### .SetInMap - -Takes a `key`, `mapKey` and `value` and adds a map of `mapKey` and `value` to the given `key`. - -```go-html-template -{{ .Store.SetInMap "greetings" "english" "Hello" }} -{{ .Store.SetInMap "greetings" "french" "Bonjour" }} - -{{ .Store.Get "greetings" }} → map[french:Bonjour english:Hello] -``` - -#### .DeleteInMap - -Takes a `key` and `mapKey` and removes the map of `mapKey` from the given `key`. - -```go-html-template -{{ .Store.SetInMap "greetings" "english" "Hello" }} -{{ .Store.SetInMap "greetings" "french" "Bonjour" }} -{{ .Store.DeleteInMap "greetings" "english" }} - -{{ .Store.Get "greetings" }} → map[french:Bonjour] -``` - -#### .GetSortedMapValues - -Returns an array of values from `key` sorted by `mapKey`. - -```go-html-template -{{ .Store.SetInMap "greetings" "english" "Hello" }} -{{ .Store.SetInMap "greetings" "french" "Bonjour" }} - -{{ .Store.GetSortedMapValues "greetings" }} → [Hello Bonjour] -``` - -#### .Delete - -Removes the given key. - -```go-html-template -{{ .Store.Set "greeting" "Hello" }} - -{{ .Store.Delete "greeting" }} -``` diff --git a/content/en/functions/string.md b/content/en/functions/string.md deleted file mode 100644 index df9d07116..000000000 --- a/content/en/functions/string.md +++ /dev/null @@ -1,48 +0,0 @@ ---- -title: string -description: Cast a value to a string. -categories: [functions] -menu: - docs: - parent: functions -keywords: [cast,strings] -signature: ["string INPUT"] -relatedfuncs: [] ---- - -With a decimal (base 10) input: - -```go-html-template -{{ string 11 }} → 11 (string) -{{ string "11" }} → 11 (string) - -{{ string 11.1 }} → 11.1 (string) -{{ string "11.1" }} → 11.1 (string) - -{{ string 11.9 }} → 11.9 (string) -{{ string "11.9" }} → 11.9 (string) -``` - -With a binary (base 2) input: - -```go-html-template -{{ string 0b11 }} → 3 (string) -{{ string "0b11" }} → 0b11 (string) -``` - -With an octal (base 8) input (use either notation): - -```go-html-template -{{ string 011 }} → 9 (string) -{{ string "011" }} → 011 (string) - -{{ string 0o11 }} → 9 (string) -{{ string "0o11" }} → 0o11 (string) -``` - -With a hexadecimal (base 16) input: - -```go-html-template -{{ string 0x11 }} → 17 (string) -{{ string "0x11" }} → 0x11 (string) -``` diff --git a/content/en/functions/strings.Contains.md b/content/en/functions/strings.Contains.md deleted file mode 100644 index 44cb73b81..000000000 --- a/content/en/functions/strings.Contains.md +++ /dev/null @@ -1,17 +0,0 @@ ---- -title: strings.Contains -description: Reports whether a string contains a substring. -categories: [functions] -menu: - docs: - parent: functions -keywords: [string strings substring contains] -signature: ["strings.Contains STRING SUBSTRING"] -relatedfuncs: [strings.ContainsAny] ---- - - {{ strings.Contains "Hugo" "go" }} → true - -The check is case sensitive: - - {{ strings.Contains "Hugo" "Go" }} → false diff --git a/content/en/functions/strings.ContainsAny.md b/content/en/functions/strings.ContainsAny.md deleted file mode 100644 index 36fa8701b..000000000 --- a/content/en/functions/strings.ContainsAny.md +++ /dev/null @@ -1,17 +0,0 @@ ---- -title: strings.ContainsAny -description: Reports whether a string contains any character from a given string. -categories: [functions] -menu: - docs: - parent: functions -keywords: [string strings substring contains any] -signature: ["strings.ContainsAny STRING CHARACTERS"] -relatedfuncs: [strings.Contains] ---- - - {{ strings.ContainsAny "Hugo" "gm" }} → true - -The check is case sensitive: - - {{ strings.ContainsAny "Hugo" "Gm" }} → false diff --git a/content/en/functions/strings.ContainsNonSpace.md b/content/en/functions/strings.ContainsNonSpace.md deleted file mode 100644 index eafe292f5..000000000 --- a/content/en/functions/strings.ContainsNonSpace.md +++ /dev/null @@ -1,27 +0,0 @@ ---- -title: strings.ContainsNonSpace -description: Reports whether a string contains any non-space characters as defined by Unicode’s White Space property. -categories: [functions] -menu: - docs: - parent: functions -keywords: [whitespace space] -signature: ["strings.ContainsNonSpace STRING"] -relatedfuncs: ["strings.Contains","strings.ContainsAny"] ---- - -```go-html-template -{{ strings.ContainsNonSpace "\n" }} → false -{{ strings.ContainsNonSpace " " }} → false -{{ strings.ContainsNonSpace "\n abc" }} → true -``` - -Common white space characters include: - -```text -'\t', '\n', '\v', '\f', '\r', ' ' -``` - -See the [Unicode Character Database] for a complete list. - -[Unicode Character Database]: https://www.unicode.org/Public/UCD/latest/ucd/PropList.txt diff --git a/content/en/functions/strings.Count.md b/content/en/functions/strings.Count.md deleted file mode 100644 index 7c3945693..000000000 --- a/content/en/functions/strings.Count.md +++ /dev/null @@ -1,20 +0,0 @@ ---- -title: strings.Count -description: Returns the number of non-overlapping instances of a substring within a string. -categories: [functions] -menu: - docs: - parent: functions -keywords: [count, counting, character count] -signature: ["strings.Count SUBSTR STRING"] -relatedfuncs: [] ---- - -If `SUBSTR` is an empty string, this function returns 1 plus the number of Unicode code points in `STRING`. - -Example|Result -:--|:-- -`{{ "aaabaab" \| strings.Count "a" }}`|5 -`{{ "aaabaab" \| strings.Count "aa" }}`|2 -`{{ "aaabaab" \| strings.Count "aaa" }}`|1 -`{{ "aaabaab" \| strings.Count "" }}`|8 diff --git a/content/en/functions/strings.FirstUpper.md b/content/en/functions/strings.FirstUpper.md deleted file mode 100644 index fab82a2dc..000000000 --- a/content/en/functions/strings.FirstUpper.md +++ /dev/null @@ -1,12 +0,0 @@ ---- -title: strings.FirstUpper -description: Capitalizes the first character of a given string. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings capitalize uppercase first] -signature: ["strings.FirstUpper STRING"] ---- - - {{ strings.FirstUpper "foo" }} → "Foo" diff --git a/content/en/functions/strings.HasPrefix.md b/content/en/functions/strings.HasPrefix.md deleted file mode 100644 index 70317a4c1..000000000 --- a/content/en/functions/strings.HasPrefix.md +++ /dev/null @@ -1,16 +0,0 @@ ---- -title: strings.HasPrefix -description: Tests whether a string begins with prefix. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["hasPrefix STRING PREFIX","strings.HasPrefix STRING PREFIX"] -relatedfuncs: [hasSuffix] -aliases: [/functions/hasprefix/] ---- - -```go-html-template -{{ hasPrefix "Hugo" "Hu" }} → true -``` diff --git a/content/en/functions/strings.HasSuffix.md b/content/en/functions/strings.HasSuffix.md deleted file mode 100644 index 3ead121a3..000000000 --- a/content/en/functions/strings.HasSuffix.md +++ /dev/null @@ -1,16 +0,0 @@ ---- -title: strings.HasSuffix -description: Tests whether a string ends with suffix. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["hasSuffix STRING SUFFIX","strings.HasSuffix STRING SUFFIX"] -relatedfuncs: [hasPrefix] -aliases: [/functions/hassuffix/] ---- - -```go-html-template -{{ hasSuffix "Hugo" "go" }} → true -``` diff --git a/content/en/functions/strings.Repeat.md b/content/en/functions/strings.Repeat.md deleted file mode 100644 index 99b2fe5a5..000000000 --- a/content/en/functions/strings.Repeat.md +++ /dev/null @@ -1,16 +0,0 @@ ---- -title: strings.Repeat -description: Returns INPUT repeated COUNT times. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["strings.Repeat COUNT INPUT"] -relatedfuncs: [] ---- - -```go-html-template -{{ strings.Repeat 3 "yo" }} → "yoyoyo" -{{ "yo" | strings.Repeat 3 }} → "yoyoyo" -``` diff --git a/content/en/functions/strings.RuneCount.md b/content/en/functions/strings.RuneCount.md deleted file mode 100644 index 3a72e339a..000000000 --- a/content/en/functions/strings.RuneCount.md +++ /dev/null @@ -1,20 +0,0 @@ ---- -title: strings.RuneCount -description: Determines the number of runes in a string. -categories: [functions] -menu: - docs: - parent: functions -keywords: [counting, character count, length, rune length, rune count] -signature: ["strings.RuneCount INPUT"] -relatedfuncs: ["len", "countrunes"] ---- - -In contrast with `strings.CountRunes` function, which strips HTML and whitespace before counting runes, `strings.RuneCount` simply counts all the runes in a string. It relies on the Go [`utf8.RuneCountInString`] function. - -```go-html-template -{{ "Hello, 世界" | strings.RuneCount }} - -``` - -[`utf8.RuneCount`]: https://golang.org/pkg/unicode/utf8/#RuneCount diff --git a/content/en/functions/strings.TrimLeft.md b/content/en/functions/strings.TrimLeft.md deleted file mode 100644 index b0271c8a8..000000000 --- a/content/en/functions/strings.TrimLeft.md +++ /dev/null @@ -1,19 +0,0 @@ ---- -title: strings.TrimLeft -description: Returns a slice of a given string with all leading characters contained in the cutset removed. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["strings.TrimLeft CUTSET STRING"] -relatedfuncs: [strings.TrimRight] ---- - -Given the string `"abba"`, leading `"a"`'s can be removed a follows: - - {{ strings.TrimLeft "a" "abba" }} → "bba" - -Numbers can be handled as well: - - {{ strings.TrimLeft 12 1221341221 }} → "341221" diff --git a/content/en/functions/strings.TrimPrefix.md b/content/en/functions/strings.TrimPrefix.md deleted file mode 100644 index c3f702961..000000000 --- a/content/en/functions/strings.TrimPrefix.md +++ /dev/null @@ -1,17 +0,0 @@ ---- -title: strings.TrimPrefix -description: Returns a given string s without the provided leading prefix string. If s doesn't start with prefix, s is returned unchanged. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["strings.TrimPrefix PREFIX STRING"] -relatedfuncs: [strings.TrimSuffix] ---- - -Given the string `"aabbaa"`, the specified prefix is only removed if `"aabbaa"` starts with it: - - {{ strings.TrimPrefix "a" "aabbaa" }} → "abbaa" - {{ strings.TrimPrefix "aa" "aabbaa" }} → "bbaa" - {{ strings.TrimPrefix "aaa" "aabbaa" }} → "aabbaa" diff --git a/content/en/functions/strings.TrimRight.md b/content/en/functions/strings.TrimRight.md deleted file mode 100644 index e61b884cd..000000000 --- a/content/en/functions/strings.TrimRight.md +++ /dev/null @@ -1,19 +0,0 @@ ---- -title: strings.TrimRight -description: Returns a slice of a given string with all trailing characters contained in the cutset removed. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["strings.TrimRight CUTSET STRING"] -relatedfuncs: [strings.TrimRight] ---- - -Given the string `"abba"`, trailing `"a"`'s can be removed a follows: - - {{ strings.TrimRight "a" "abba" }} → "abb" - -Numbers can be handled as well: - - {{ strings.TrimRight 12 1221341221 }} → "122134" diff --git a/content/en/functions/strings.TrimSuffix.md b/content/en/functions/strings.TrimSuffix.md deleted file mode 100644 index 05bb92400..000000000 --- a/content/en/functions/strings.TrimSuffix.md +++ /dev/null @@ -1,17 +0,0 @@ ---- -title: strings.TrimSuffix -description: Returns a given string s without the provided trailing suffix string. If s doesn't end with suffix, s is returned unchanged. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: ["strings.TrimSuffix SUFFIX STRING"] -relatedfuncs: [strings.TrimPrefix] ---- - -Given the string `"aabbaa"`, the specified suffix is only removed if `"aabbaa"` ends with it: - - {{ strings.TrimSuffix "a" "aabbaa" }} → "aabba" - {{ strings.TrimSuffix "aa" "aabbaa" }} → "aabb" - {{ strings.TrimSuffix "aaa" "aabbaa" }} → "aabbaa" diff --git a/content/en/functions/strings/Chomp.md b/content/en/functions/strings/Chomp.md new file mode 100644 index 000000000..22e2b546b --- /dev/null +++ b/content/en/functions/strings/Chomp.md @@ -0,0 +1,31 @@ +--- +title: chomp +linkTitle: chomp +description: Removes any trailing newline characters. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [chomp] + returnType: any + signatures: [strings.Chomp STRING] +relatedFunctions: + - strings.Chomp + - strings.Trim + - strings.TrimLeft + - strings.TrimPrefix + - strings.TrimRight + - strings.TrimSuffix +aliases: [/functions/chomp] +--- + +If the argument is of type template.HTML, returns template.HTML, else returns a string. + + +Useful in a pipeline to remove newlines added by other processing (e.g., [`markdownify`](/functions/transform/markdownify)). + +```go-html-template +{{ chomp "

Blockhead

\n" }} → "

Blockhead

" +``` diff --git a/content/en/functions/strings/Contains.md b/content/en/functions/strings/Contains.md new file mode 100644 index 000000000..66a90aeea --- /dev/null +++ b/content/en/functions/strings/Contains.md @@ -0,0 +1,29 @@ +--- +title: strings.Contains +description: Reports whether the string contains a substring. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: bool + signatures: [strings.Contains STRING SUBSTRING] +relatedFunctions: + - strings.Contains + - strings.ContainsAny + - strings.ContainsNonSpace + - strings.HasPrefix + - strings.HasSuffix +aliases: [/functions/strings.contains] +--- + +```go-html-template +{{ strings.Contains "Hugo" "go" }} → true +``` +The check is case sensitive: + +```go-html-template +{{ strings.Contains "Hugo" "Go" }} → false +``` diff --git a/content/en/functions/strings/ContainsAny.md b/content/en/functions/strings/ContainsAny.md new file mode 100644 index 000000000..4f324358a --- /dev/null +++ b/content/en/functions/strings/ContainsAny.md @@ -0,0 +1,30 @@ +--- +title: strings.ContainsAny +description: Reports whether a string contains any character from a given string. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: bool + signatures: [strings.ContainsAny STRING CHARACTERS] +relatedFunctions: + - strings.Contains + - strings.ContainsAny + - strings.ContainsNonSpace + - strings.HasPrefix + - strings.HasSuffix +aliases: [/functions/strings.containsany] +--- + +```go-html-template +{{ strings.ContainsAny "Hugo" "gm" }} → true +``` + +The check is case sensitive: + +```go-html-template +{{ strings.ContainsAny "Hugo" "Gm" }} → false +``` diff --git a/content/en/functions/strings/ContainsNonSpace.md b/content/en/functions/strings/ContainsNonSpace.md new file mode 100644 index 000000000..d2e6114b3 --- /dev/null +++ b/content/en/functions/strings/ContainsNonSpace.md @@ -0,0 +1,36 @@ +--- +title: strings.ContainsNonSpace +description: Reports whether a string contains any non-space characters as defined by Unicode’s White Space property. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: bool + signatures: [strings.ContainsNonSpace STRING] +relatedFunctions: + - strings.Contains + - strings.ContainsAny + - strings.ContainsNonSpace + - strings.HasPrefix + - strings.HasSuffix +aliases: [/functions/strings.containsnonspace] +--- + +```go-html-template +{{ strings.ContainsNonSpace "\n" }} → false +{{ strings.ContainsNonSpace " " }} → false +{{ strings.ContainsNonSpace "\n abc" }} → true +``` + +Common white space characters include: + +```text +'\t', '\n', '\v', '\f', '\r', ' ' +``` + +See the [Unicode Character Database] for a complete list. + +[Unicode Character Database]: https://www.unicode.org/Public/UCD/latest/ucd/PropList.txt diff --git a/content/en/functions/strings/Count.md b/content/en/functions/strings/Count.md new file mode 100644 index 000000000..25ea58967 --- /dev/null +++ b/content/en/functions/strings/Count.md @@ -0,0 +1,29 @@ +--- +title: strings.Count +description: Returns the number of non-overlapping instances of a substring within a string. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: int + signatures: [strings.Count SUBSTR STRING] +relatedFunctions: + - len + - strings.Count + - strings.CountRunes + - strings.CountWords + - strings.RuneCount +aliases: [/functions/strings.count] +--- + +If `SUBSTR` is an empty string, this function returns 1 plus the number of Unicode code points in `STRING`. + +```go-html-template +{{ "aaabaab" | strings.Count "a" }} → 5 +{{ "aaabaab" | strings.Count "aa" }} → 2 +{{ "aaabaab" | strings.Count "aaa" }} → 1 +{{ "aaabaab" | strings.Count "" }} → 8 +``` diff --git a/content/en/functions/strings/CountRunes.md b/content/en/functions/strings/CountRunes.md new file mode 100644 index 000000000..4a17d04ab --- /dev/null +++ b/content/en/functions/strings/CountRunes.md @@ -0,0 +1,29 @@ +--- +title: strings.CountRunes +linkTitle: countrunes +description: Returns the number of runes in a string excluding whitespace. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [countrunes] + returnType: int + signatures: [strings.CountRunes INPUT] +relatedFunctions: + - len + - strings.Count + - strings.CountRunes + - strings.CountWords + - strings.RuneCount +aliases: [/functions/countrunes] +--- + +In contrast with the [`strings.RuneCount`] function, which counts every rune in a string, `strings.CountRunes` excludes whitespace. + +```go-html-template +{{ "Hello, 世界" | strings.CountRunes }} → 8 +``` + +[`strings.RuneCount`]: /functions/strings/runecount diff --git a/content/en/functions/strings/CountWords.md b/content/en/functions/strings/CountWords.md new file mode 100644 index 000000000..e6915e6cd --- /dev/null +++ b/content/en/functions/strings/CountWords.md @@ -0,0 +1,31 @@ +--- +title: strings.CountWords +linkTitle: countwords +description: Counts the number of words in a string. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [countwords] + returnType: int + signatures: [strings.CountWords INPUT] +relatedFunctions: + - len + - strings.Count + - strings.CountRunes + - strings.CountWords + - strings.RuneCount +aliases: [/functions/countwords] +--- + +The template function works similar to the [.WordCount page variable][pagevars]. + +```go-html-template +{{ "Hugo is a static site generator." | countwords }} + +``` + + +[pagevars]: /variables/page/ diff --git a/content/en/functions/strings/FindRESubmatch.md b/content/en/functions/strings/FindRESubmatch.md new file mode 100644 index 000000000..5a0410fdb --- /dev/null +++ b/content/en/functions/strings/FindRESubmatch.md @@ -0,0 +1,95 @@ +--- +title: strings.FindRESubmatch +linkTitle: findRESubmatch +description: Returns a slice of all successive matches of the regular expression. Each element is a slice of strings holding the text of the leftmost match of the regular expression and the matches, if any, of its subexpressions. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [findRESubmatch] + returnType: '[]string' + signatures: ['strings.FindRESubmatch PATTERN INPUT [LIMIT]'] +relatedFunctions: + - strings.FindRE + - strings.FindRESubmatch + - strings.Replace + - strings.ReplaceRE +aliases: [/functions/findresubmatch] +--- + +By default, `findRESubmatch` finds all matches. You can limit the number of matches with an optional LIMIT argument. A return value of nil indicates no match. + +{{% readfile file="/functions/_common/regular-expressions.md" %}} + +## Demonstrative examples + +```go-html-template +{{ findRESubmatch `a(x*)b` "-ab-" }} → [["ab" ""]] +{{ findRESubmatch `a(x*)b` "-axxb-" }} → [["axxb" "xx"]] +{{ findRESubmatch `a(x*)b` "-ab-axb-" }} → [["ab" ""] ["axb" "x"]] +{{ findRESubmatch `a(x*)b` "-axxb-ab-" }} → [["axxb" "xx"] ["ab" ""]] +{{ findRESubmatch `a(x*)b` "-axxb-ab-" 1 }} → [["axxb" "xx"]] +``` + +## Practical example + +This markdown: + +```text +- [Example](https://example.org) +- [Hugo](https://gohugo.io) +``` + +Produces this HTML: + +```html + +``` + +To match the anchor elements, capturing the link destination and text: + +```go-html-template +{{ $regex := `(.+?)` }} +{{ $matches := findRESubmatch $regex .Content }} +``` + +Viewed as JSON, the data structure of `$matches` in the code above is: + +```json +[ + [ + "Example", + "https://example.org", + "Example" + ], + [ + "Hugo", + "https://gohugo.io", + "Hugo" + ] +] +``` + +To render the `href` attributes: + +```go-html-template +{{ range $matches }} + {{ index . 1 }} +{{ end }} +``` + +Result: + +```text +https://example.org +https://gohugo.io +``` + +{{% note %}} +You can write and test your regular expression using [regex101.com](https://regex101.com/). Be sure to select the Go flavor before you begin. +{{% /note %}} diff --git a/content/en/functions/strings/FindRe.md b/content/en/functions/strings/FindRe.md new file mode 100644 index 000000000..4a7811f3d --- /dev/null +++ b/content/en/functions/strings/FindRe.md @@ -0,0 +1,41 @@ +--- +title: strings.FindRE +linkTitle: findRE +description: Returns a slice of strings that match the regular expression. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [findRE] + returnType: string + signatures: ['strings.FindRE PATTERN INPUT [LIMIT]'] +relatedFunctions: + - strings.FindRE + - strings.FindRESubmatch + - strings.Replace + - strings.ReplaceRE +aliases: [/functions/findre] +--- +By default, `findRE` finds all matches. You can limit the number of matches with an optional LIMIT argument. + +{{% readfile file="/functions/_common/regular-expressions.md" %}} + +This example returns a slice of all second level headings (`h2` elements) within the rendered `.Content`: + +```go-html-template +{{ findRE `(?s).*?` .Content }} +``` + +The `s` flag causes `.` to match `\n` as well, allowing us to find an `h2` element that contains newlines. + +To limit the number of matches to one: + +```go-html-template +{{ findRE `(?s).*?` .Content 1 }} +``` + +{{% note %}} +You can write and test your regular expression using [regex101.com](https://regex101.com/). Be sure to select the Go flavor before you begin. +{{% /note %}} diff --git a/content/en/functions/strings/FirstUpper.md b/content/en/functions/strings/FirstUpper.md new file mode 100644 index 000000000..320f01eda --- /dev/null +++ b/content/en/functions/strings/FirstUpper.md @@ -0,0 +1,23 @@ +--- +title: strings.FirstUpper +description: Capitalizes the first character of a given string. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: string + signatures: [strings.FirstUpper STRING] +relatedFunctions: + - strings.FirstUpper + - strings.Title + - strings.ToLower + - strings.ToUpper +aliases: [/functions/strings.firstupper] +--- + +```go-html-template +{{ strings.FirstUpper "foo" }} → "Foo" +``` diff --git a/content/en/functions/strings/HasPrefix.md b/content/en/functions/strings/HasPrefix.md new file mode 100644 index 000000000..88a79a935 --- /dev/null +++ b/content/en/functions/strings/HasPrefix.md @@ -0,0 +1,24 @@ +--- +title: strings.HasPrefix +description: Reports whether a string begins with prefix. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [hasPrefix] + returnType: bool + signatures: [strings.HasPrefix STRING PREFIX] +relatedFunctions: + - strings.Contains + - strings.ContainsAny + - strings.ContainsNonSpace + - strings.HasPrefix + - strings.HasSuffix +aliases: [/functions/hasprefix,/functions/strings.hasprefix] +--- + +```go-html-template +{{ hasPrefix "Hugo" "Hu" }} → true +``` diff --git a/content/en/functions/strings/HasSuffix.md b/content/en/functions/strings/HasSuffix.md new file mode 100644 index 000000000..d11f3e8cf --- /dev/null +++ b/content/en/functions/strings/HasSuffix.md @@ -0,0 +1,24 @@ +--- +title: strings.HasSuffix +description: Reports whether a string ends with suffix. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [hasSuffix] + returnType: bool + signatures: [strings.HasSuffix STRING SUFFIX] +relatedFunctions: + - strings.Contains + - strings.ContainsAny + - strings.ContainsNonSpace + - strings.HasPrefix + - strings.HasSuffix +aliases: [/functions/hassuffix,/functions/strings/hassuffix] +--- + +```go-html-template +{{ hasSuffix "Hugo" "go" }} → true +``` diff --git a/content/en/functions/strings/Repeat.md b/content/en/functions/strings/Repeat.md new file mode 100644 index 000000000..718f24984 --- /dev/null +++ b/content/en/functions/strings/Repeat.md @@ -0,0 +1,20 @@ +--- +title: strings.Repeat +description: Returns a new string consisting of zero or more copies of another string. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: string + signatures: [strings.Repeat COUNT INPUT] +relatedFunctions: [] +aliases: [/functions/strings.repeat] +--- + +```go-html-template +{{ strings.Repeat 3 "yo" }} → "yoyoyo" +{{ "yo" | strings.Repeat 3 }} → "yoyoyo" +``` diff --git a/content/en/functions/strings/Replace.md b/content/en/functions/strings/Replace.md new file mode 100644 index 000000000..8d5e54859 --- /dev/null +++ b/content/en/functions/strings/Replace.md @@ -0,0 +1,30 @@ +--- +title: strings.Replace +linkTitle: replace +description: Replaces all occurrences of the search string with the replacement string. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [replace] + returnType: string + signatures: ['strings.Replace INPUT OLD NEW [LIMIT]'] +relatedFunctions: + - strings.FindRE + - strings.FindRESubmatch + - strings.Replace + - strings.ReplaceRE +aliases: [/functions/replace] +--- + +Replace returns a copy of `INPUT` with all occurrences of `OLD` replaced with `NEW`. +The number of replacements can be limited with an optional `LIMIT` argument. + +``` +{{ replace "Batman and Robin" "Robin" "Catwoman" }} +→ "Batman and Catwoman" + +{{ replace "aabbaabb" "a" "z" 2 }} → "zzbbaabb" +``` diff --git a/content/en/functions/strings/ReplaceRE.md b/content/en/functions/strings/ReplaceRE.md new file mode 100644 index 000000000..247595877 --- /dev/null +++ b/content/en/functions/strings/ReplaceRE.md @@ -0,0 +1,51 @@ +--- +title: strings.ReplaceRE +linkTitle: replaceRE +description: Returns a string, replacing all occurrences of a regular expression with a replacement pattern. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [replaceRE] + returnType: string + signatures: ['strings.ReplaceRE PATTERN REPLACEMENT INPUT [LIMIT]'] +relatedFunctions: + - strings.FindRE + - strings.FindRESubmatch + - strings.Replace + - strings.ReplaceRE +aliases: [/functions/replacere] +--- +By default, `replaceRE` replaces all matches. You can limit the number of matches with an optional LIMIT argument. + +{{% readfile file="/functions/_common/regular-expressions.md" %}} + +This example replaces two or more consecutive hyphens with a single hyphen: + +```go-html-template +{{ $s := "a-b--c---d" }} +{{ replaceRE `(-{2,})` "-" $s }} → a-b-c-d +``` + +To limit the number of replacements to one: + +```go-html-template +{{ $s := "a-b--c---d" }} +{{ replaceRE `(-{2,})` "-" $s 1 }} → a-b-c---d +``` + +You can use `$1`, `$2`, etc. within the replacement string to insert the groups captured within the regular expression: + +```go-html-template +{{ $s := "http://gohugo.io/docs" }} +{{ replaceRE "^https?://([^/]+).*" "$1" $s }} → gohugo.io +``` + +{{% note %}} +You can write and test your regular expression using [regex101.com](https://regex101.com/). Be sure to select the Go flavor before you begin. +{{% /note %}} + +[RE2]: https://github.com/google/re2/wiki/Syntax +[string literal]: https://go.dev/ref/spec#String_literals diff --git a/content/en/functions/strings/RuneCount.md b/content/en/functions/strings/RuneCount.md new file mode 100644 index 000000000..a4d5a8dbe --- /dev/null +++ b/content/en/functions/strings/RuneCount.md @@ -0,0 +1,28 @@ +--- +title: strings.RuneCount +description: Returns the number of runes in a string. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: int + signatures: [strings.RuneCount INPUT] +relatedFunctions: + - len + - strings.Count + - strings.CountRunes + - strings.CountWords + - strings.RuneCount +aliases: [/functions/strings.runecount] +--- + +In contrast with the [`strings.CountRunes`] function, which excludes whitespace, `strings.RuneCount` counts every rune in a string. + +```go-html-template +{{ "Hello, 世界" | strings.RuneCount }} → 9 +``` + +[`strings.CountRunes`]: /functions/strings/countrunes diff --git a/content/en/functions/strings/SliceString.md b/content/en/functions/strings/SliceString.md new file mode 100644 index 000000000..8d26d76e4 --- /dev/null +++ b/content/en/functions/strings/SliceString.md @@ -0,0 +1,24 @@ +--- +title: strings.SliceString +linkTitle: slicestr +description: Creates a slice of a half-open range, including start and end indices. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [slicestr] + returnType: string + signatures: ['strings.SliceString STRING START [END]'] +relatedFunctions: [] +aliases: [/functions/slicestr] +--- + +For example, 1 and 4 creates a slice including elements 1 through 3. +The `end` index can be omitted; it defaults to the string's length. + +```go-html-template +{{ slicestr "BatMan" 3 }}` → "Man" +{{ slicestr "BatMan" 0 3 }}` → "Bat" +``` diff --git a/content/en/functions/strings/Split.md b/content/en/functions/strings/Split.md new file mode 100644 index 000000000..7d15704b2 --- /dev/null +++ b/content/en/functions/strings/Split.md @@ -0,0 +1,30 @@ +--- +title: strings.Split +linkTitle: split +description: Returns a slice of strings by splitting STRING by DELIM. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [split] + returnType: string + signatures: [strings.Split STRING DELIM] +relatedFunctions: + - collections.Delimit + - strings.Split +aliases: [/functions/split] +--- + +Examples: + +```go-html-template +{{ split "tag1,tag2,tag3" "," }} → ["tag1", "tag2", "tag3"] +{{ split "abc" "" }} → ["a", "b", "c"] +``` + + +{{% note %}} +`split` essentially does the opposite of [delimit](/functions/collections/delimit). While `split` creates a slice from a string, `delimit` creates a string from a slice. +{{% /note %}} diff --git a/content/en/functions/strings/Substr.md b/content/en/functions/strings/Substr.md new file mode 100644 index 000000000..9dafa0737 --- /dev/null +++ b/content/en/functions/strings/Substr.md @@ -0,0 +1,42 @@ +--- +title: strings.Substr +linkTitle: substr +description: Extracts parts of a string from a specified character's position and returns the specified number of characters. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [substr] + returnType: string + signatures: ['strings.Substr STRING START [LENGTH]'] +relatedFunctions: [] +aliases: [/functions/substr] +--- + +It normally takes two argument: `start` and `length`. It can also take one argument: `start`, i.e. `length` is omitted, in which case the substring starting from start until the end of the string will be returned. + +To extract characters from the end of the string, use a negative start number. + +If `length` is given and is negative, that number of characters will be omitted from the end of string. + +```go-html-template +{{ substr "abcdef" 0 }} → "abcdef" +{{ substr "abcdef" 1 }} → "bcdef" + +{{ substr "abcdef" 0 1 }} → "a" +{{ substr "abcdef" 1 1 }} → "b" + +{{ substr "abcdef" 0 -1 }} → "abcde" +{{ substr "abcdef" 1 -1 }} → "bcde" + +{{ substr "abcdef" -1 }} → "f" +{{ substr "abcdef" -2 }} → "ef" + +{{ substr "abcdef" -1 1 }} → "f" +{{ substr "abcdef" -2 1 }} → "e" + +{{ substr "abcdef" -3 -1 }} → "de" +{{ substr "abcdef" -3 -2 }} → "d" +``` diff --git a/content/en/functions/strings/Title.md b/content/en/functions/strings/Title.md new file mode 100644 index 000000000..1e20d1f59 --- /dev/null +++ b/content/en/functions/strings/Title.md @@ -0,0 +1,30 @@ +--- +title: strings.Title +linkTitle: title +description: Converts the provided string to title case. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [title] + returnType: string + signatures: [strings.Title STRING] +relatedFunctions: + - strings.FirstUpper + - strings.Title + - strings.ToLower + - strings.ToUpper +aliases: [/functions/title] +--- + +```go-html-template +{{ title "table of contents (TOC)" }} → "Table of Contents (TOC)" +``` + +By default, Hugo adheres to the capitalization rules in the [Associated Press (AP) Stylebook]. Change your [site configuration] if you would prefer to follow the [Chicago Manual of Style], or to use Go's convention of capitalizing every word. + +[Associated Press (AP) Stylebook]: https://www.apstylebook.com/ +[Chicago Manual of Style]: https://www.chicagomanualofstyle.org/home.html +[site configuration]: /getting-started/configuration/#configure-title-case diff --git a/content/en/functions/strings/ToLower.md b/content/en/functions/strings/ToLower.md new file mode 100644 index 000000000..cb76462ea --- /dev/null +++ b/content/en/functions/strings/ToLower.md @@ -0,0 +1,28 @@ +--- +title: strings.ToLower +linkTitle: lower +description: Converts all characters in the provided string to lowercase. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [lower] + returnType: string + signatures: [strings.ToLower INPUT] +relatedFunctions: + - strings.FirstUpper + - strings.Title + - strings.ToLower + - strings.ToUpper +aliases: [/functions/lower] +--- + + +Note that `lower` can be applied in your templates in more than one way: + +```go-html-template +{{ lower "BatMan" }} → "batman" +{{ "BatMan" | lower }} → "batman" +``` diff --git a/content/en/functions/strings/ToUpper.md b/content/en/functions/strings/ToUpper.md new file mode 100644 index 000000000..d46491637 --- /dev/null +++ b/content/en/functions/strings/ToUpper.md @@ -0,0 +1,27 @@ +--- +title: strings.ToUpper +linkTitle: upper +description: Converts all characters in a string to uppercase +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [upper] + returnType: string + signatures: [strings.ToUpper INPUT] +relatedFunctions: + - strings.FirstUpper + - strings.Title + - strings.ToLower + - strings.ToUpper +aliases: [/functions/upper] +--- + +Note that `upper` can be applied in your templates in more than one way: + +```go-html-template +{{ upper "BatMan" }} → "BATMAN" +{{ "BatMan" | upper }} → "BATMAN" +``` diff --git a/content/en/functions/strings/Trim.md b/content/en/functions/strings/Trim.md new file mode 100644 index 000000000..9eae9ee45 --- /dev/null +++ b/content/en/functions/strings/Trim.md @@ -0,0 +1,45 @@ +--- +title: strings.Trim +linkTitle: trim +description: Returns a slice of a passed string with all leading and trailing characters from cutset removed. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [title] + returnType: string + signatures: [strings.Trim INPUT CUTSET] +relatedFunctions: + - strings.Chomp + - strings.Trim + - strings.TrimLeft + - strings.TrimPrefix + - strings.TrimRight + - strings.TrimSuffix +aliases: [/functions/trim] +--- + +```go-html-template +{{ trim "++Batman--" "+-" }} → "Batman" +``` + +`trim` *requires* the second argument, which tells the function specifically what to remove from the first argument. There is no default value for the second argument, so **the following usage will not work**: + +```go-html-template +{{ trim .Inner }} +``` + +Instead, the following example tells `trim` to remove extra new lines from the content contained in the [shortcode `.Inner` variable][shortcodevars]: + +```go-html-template +{{ trim .Inner "\n" }} +``` + +{{% note %}} +Go templates also provide a simple [method for trimming whitespace](/templates/introduction/#whitespace) from either side of a Go tag by including a hyphen (`-`). +{{% /note %}} + + +[shortcodevars]: /variables/shortcodes/ diff --git a/content/en/functions/strings/TrimLeft.md b/content/en/functions/strings/TrimLeft.md new file mode 100644 index 000000000..3924e492f --- /dev/null +++ b/content/en/functions/strings/TrimLeft.md @@ -0,0 +1,33 @@ +--- +title: strings.TrimLeft +description: Returns a slice of a given string with all leading characters contained in the cutset removed. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: string + signatures: [strings.TrimLeft CUTSET STRING] +relatedFunctions: + - strings.Chomp + - strings.Trim + - strings.TrimLeft + - strings.TrimPrefix + - strings.TrimRight + - strings.TrimSuffix +aliases: [/functions/strings.trimleft] +--- + +Given the string `"abba"`, leading `"a"`'s can be removed a follows: + +```go-html-template +{{ strings.TrimLeft "a" "abba" }} → "bba" +``` + +Numbers can be handled as well: + +```go-html-template +{{ strings.TrimLeft 12 1221341221 }} → "341221" +``` diff --git a/content/en/functions/strings/TrimPrefix.md b/content/en/functions/strings/TrimPrefix.md new file mode 100644 index 000000000..37657732d --- /dev/null +++ b/content/en/functions/strings/TrimPrefix.md @@ -0,0 +1,29 @@ +--- +title: strings.TrimPrefix +description: Returns a given string s without the provided leading prefix string. If s doesn't start with prefix, s is returned unchanged. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: string + signatures: [strings.TrimPrefix PREFIX STRING] +relatedFunctions: + - strings.Chomp + - strings.Trim + - strings.TrimLeft + - strings.TrimPrefix + - strings.TrimRight + - strings.TrimSuffix +aliases: [/functions/strings.trimprefix] +--- + +Given the string `"aabbaa"`, the specified prefix is only removed if `"aabbaa"` starts with it: + +```go-html-template +{{ strings.TrimPrefix "a" "aabbaa" }} → "abbaa" +{{ strings.TrimPrefix "aa" "aabbaa" }} → "bbaa" +{{ strings.TrimPrefix "aaa" "aabbaa" }} → "aabbaa" +``` diff --git a/content/en/functions/strings/TrimRight.md b/content/en/functions/strings/TrimRight.md new file mode 100644 index 000000000..fa538b605 --- /dev/null +++ b/content/en/functions/strings/TrimRight.md @@ -0,0 +1,33 @@ +--- +title: strings.TrimRight +description: Returns a slice of a given string with all trailing characters contained in the cutset removed. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: string + signatures: [strings.TrimRight CUTSET STRING] +relatedFunctions: + - strings.Chomp + - strings.Trim + - strings.TrimLeft + - strings.TrimPrefix + - strings.TrimRight + - strings.TrimSuffix +aliases: [/functions/strings.trimright] +--- + +Given the string `"abba"`, trailing `"a"`'s can be removed a follows: + +```go-html-template +{{ strings.TrimRight "a" "abba" }} → "abb" +``` + +Numbers can be handled as well: + +```go-html-template +{{ strings.TrimRight 12 1221341221 }} → "122134" +``` diff --git a/content/en/functions/strings/TrimSuffix.md b/content/en/functions/strings/TrimSuffix.md new file mode 100644 index 000000000..6dc9becfc --- /dev/null +++ b/content/en/functions/strings/TrimSuffix.md @@ -0,0 +1,29 @@ +--- +title: strings.TrimSuffix +description: Returns a given string s without the provided trailing suffix string. If s doesn't end with suffix, s is returned unchanged. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: string + signatures: [strings.TrimSuffix SUFFIX STRING] +relatedFunctions: + - strings.Chomp + - strings.Trim + - strings.TrimLeft + - strings.TrimPrefix + - strings.TrimRight + - strings.TrimSuffix +aliases: [/functions/strings.trimsuffix] +--- + +Given the string `"aabbaa"`, the specified suffix is only removed if `"aabbaa"` ends with it: + +```go-html-template +{{ strings.TrimSuffix "a" "aabbaa" }} → "aabba" +{{ strings.TrimSuffix "aa" "aabbaa" }} → "aabb" +{{ strings.TrimSuffix "aaa" "aabbaa" }} → "aabbaa" +``` diff --git a/content/en/functions/strings/Truncate.md b/content/en/functions/strings/Truncate.md new file mode 100644 index 000000000..0bd78d840 --- /dev/null +++ b/content/en/functions/strings/Truncate.md @@ -0,0 +1,26 @@ +--- +title: strings.Truncate +linkTitle: truncate +description: Truncates a text to a max length without cutting words or leaving unclosed HTML tags. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [truncate] + returnType: template.HTML + signatures: ['strings.Truncate SIZE [ELLIPSIS] INPUT'] +relatedFunctions: [] +aliases: [/functions/truncate] +--- + +Since Go templates are HTML-aware, `truncate` will intelligently handle normal strings vs HTML strings: + +```go-html-template +{{ "Keep my HTML" | safeHTML | truncate 10 }} → Keep my … +``` + +{{% note %}} +If you have a raw string that contains HTML tags you want to remain treated as HTML, you will need to convert the string to HTML using the [`safeHTML` template function](/functions/safe/html) before sending the value to truncate. Otherwise, the HTML tags will be escaped when passed through the `truncate` function. +{{% /note %}} diff --git a/content/en/functions/substr.md b/content/en/functions/substr.md deleted file mode 100644 index 90ee47b55..000000000 --- a/content/en/functions/substr.md +++ /dev/null @@ -1,39 +0,0 @@ ---- -title: substr -description: Extracts parts of a string from a specified character's position and returns the specified number of characters. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: - - "substr STRING START [LENGTH]" - - "strings.Substr STRING START [LENGTH]" -relatedfuncs: [] ---- - -It normally takes two argument: `start` and `length`. It can also take one argument: `start`, i.e. `length` is omitted, in which case the substring starting from start until the end of the string will be returned. - -To extract characters from the end of the string, use a negative start number. - -If `length` is given and is negative, that number of characters will be omitted from the end of string. - -```go-html-template -{{ substr "abcdef" 0 }} → "abcdef" -{{ substr "abcdef" 1 }} → "bcdef" - -{{ substr "abcdef" 0 1 }} → "a" -{{ substr "abcdef" 1 1 }} → "b" - -{{ substr "abcdef" 0 -1 }} → "abcde" -{{ substr "abcdef" 1 -1 }} → "bcde" - -{{ substr "abcdef" -1 }} → "f" -{{ substr "abcdef" -2 }} → "ef" - -{{ substr "abcdef" -1 1 }} → "f" -{{ substr "abcdef" -2 1 }} → "e" - -{{ substr "abcdef" -3 -1 }} → "de" -{{ substr "abcdef" -3 -2 }} → "d" -``` diff --git a/content/en/functions/symdiff.md b/content/en/functions/symdiff.md deleted file mode 100644 index ffc309418..000000000 --- a/content/en/functions/symdiff.md +++ /dev/null @@ -1,20 +0,0 @@ ---- -title: symdiff -description: "`collections.SymDiff` (alias `symdiff`) returns the symmetric difference of two collections." -categories: [functions] -menu: - docs: - parent: functions -keywords: [collections,intersect,union,complement] -signature: ["COLLECTION | symdiff COLLECTION" ] ---- - -Example: - -```go-html-template -{{ slice 1 2 3 | symdiff (slice 3 4) }} -``` - -The above will print `[1 2 4]`. - -Also see https://en.wikipedia.org/wiki/Symmetric_difference diff --git a/content/en/functions/templates.Exists.md b/content/en/functions/templates.Exists.md deleted file mode 100644 index b9f340c21..000000000 --- a/content/en/functions/templates.Exists.md +++ /dev/null @@ -1,26 +0,0 @@ ---- -title: templates.Exists -description: "Checks whether a template file exists under the given path relative to the `layouts` directory." -categories: [functions] -tags: [] -menu: - docs: - parent: functions -ns: "" -keywords: ["templates", "template", "layouts"] -signature: ["templates.Exists PATH"] -relatedfuncs: [] ---- - -A template file is any file living below the `layouts` directories of either the project or any of its theme components including partials and shortcodes. - -The function is particularly handy with dynamic path. The following example ensures the build will not break on a `.Type` missing its dedicated `header` partial. - -```go-html-template -{{ $partialPath := printf "headers/%s.html" .Type }} -{{ if templates.Exists ( printf "partials/%s" $partialPath ) }} - {{ partial $partialPath . }} -{{ else }} - {{ partial "headers/default.html" . }} -{{ end }} -``` diff --git a/content/en/functions/templates/Exists.md b/content/en/functions/templates/Exists.md new file mode 100644 index 000000000..d4a8fab76 --- /dev/null +++ b/content/en/functions/templates/Exists.md @@ -0,0 +1,29 @@ +--- +title: templates.Exists +description: Reports whether a template file exists under the given path relative to the `layouts` directory. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: bool + signatures: [templates.Exists PATH] +namespace: templates +relatedFunctions: [] +aliases: [/functions/templates.exists] +--- + +A template file is any file living below the `layouts` directories of either the project or any of its theme components including partials and shortcodes. + +The function is particularly handy with dynamic path. The following example ensures the build will not break on a `.Type` missing its dedicated `header` partial. + +```go-html-template +{{ $partialPath := printf "headers/%s.html" .Type }} +{{ if templates.Exists ( printf "partials/%s" $partialPath ) }} + {{ partial $partialPath . }} +{{ else }} + {{ partial "headers/default.html" . }} +{{ end }} +``` diff --git a/content/en/functions/time.ParseDuration.md b/content/en/functions/time.ParseDuration.md deleted file mode 100644 index 0332c1706..000000000 --- a/content/en/functions/time.ParseDuration.md +++ /dev/null @@ -1,18 +0,0 @@ ---- -title: time.ParseDuration -description: Parses a given duration string into a `time.Duration` structure. -categories: [functions] -menu: - docs: - parent: functions -keywords: [time parse duration] -signature: ["time.ParseDuration DURATION"] ---- - -`time.ParseDuration` parses a duration string into a [`time.Duration`](https://pkg.go.dev/time#Duration) structure so you can access its fields. -A duration string is a possibly signed sequence of decimal numbers, each with optional fraction and a unit suffix, such as `300ms`, `-1.5h` or `2h45m`. Valid time units are `ns`, `us` (or `µs`), `ms`, `s`, `m`, `h`. - -You can perform [time operations](https://pkg.go.dev/time#Duration) on the returned `time.Duration` value: - - {{ printf "There are %.0f seconds in one day." (time.ParseDuration "24h").Seconds }} - diff --git a/content/en/functions/time.md b/content/en/functions/time.md deleted file mode 100644 index 99182f317..000000000 --- a/content/en/functions/time.md +++ /dev/null @@ -1,54 +0,0 @@ ---- -title: time -description: Converts a timestamp string into a `time.Time` structure. -categories: [functions] -menu: - docs: - parent: functions -keywords: [dates,time,location] -signature: ["time INPUT [TIMEZONE]"] -relatedfuncs: [] ---- - - -`time` converts a timestamp string with an optional default location into a [`time.Time`](https://godoc.org/time#Time) structure so you can access its fields: - -```go-html-template -{{ time "2016-05-28" }} → "2016-05-28T00:00:00Z" -{{ (time "2016-05-28").YearDay }} → 149 -{{ mul 1000 (time "2016-05-28T10:30:00.00+10:00").Unix }} → 1464395400000, or Unix time in milliseconds -``` - -## Using locations - -The optional `TIMEZONE` argument is a string that sets a default time zone (or more specific, the location, which represents the collection of time offsets in a geographical area) that is associated with the specified time value. If the time value has an explicit timezone or offset specified, it will take precedence over the `TIMEZONE` argument. - -The list of valid locations may be system dependent, but should include `UTC`, `Local`, or any location in the [IANA Time Zone database](https://en.wikipedia.org/wiki/List_of_tz_database_time_zones). - -If no `TIMEZONE` is set, the `timeZone` from site configuration will be used. - -```go-html-template -{{ time "2020-10-20" }} → 2020-10-20 00:00:00 +0000 UTC -{{ time "2020-10-20" "America/Los_Angeles" }} → 2020-10-20 00:00:00 -0700 PDT -{{ time "2020-01-20" "America/Los_Angeles" }} → 2020-01-20 00:00:00 -0800 PST -``` - -## Example: Using `time` to get month index - -The following example takes a UNIX timestamp---set as `utimestamp: "1489276800"` in a content's front matter---converts the timestamp (string) to an integer using the [`int` function][int], and then uses [`printf`] to convert the `Month` property of `time` into an index. - -The following example may be useful when setting up [multilingual sites][multilingual]: - -{{< code file="unix-to-month-integer.html" >}} -{{ $time := time (int .Params.addDate)}} -=> $time = 1489276800 -{{ $time.Month }} -=> "March" -{{ $monthindex := printf "%d" $time.Month }} -=> $monthindex = 3 -{{< /code >}} - - -[int]: /functions/int/ -[multilingual]: /content-management/multilingual/ -[`printf`]: /functions/printf/ diff --git a/content/en/functions/time/AsTime.md b/content/en/functions/time/AsTime.md new file mode 100644 index 000000000..1244eeb5c --- /dev/null +++ b/content/en/functions/time/AsTime.md @@ -0,0 +1,64 @@ +--- +title: time.AsTime +linkTitle: time +description: Converts a timestamp string into a `time.Time` structure. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [time] + returnType: time.Time + signatures: ['time.AsTime INPUT [TIMEZONE]'] +relatedFunctions: + - time.AsTime + - time.Duration + - time.Format + - time.Now + - time.ParseDuration +aliases: [/functions/time] +--- + + +`time` converts a timestamp string with an optional default location into a [`time.Time`](https://godoc.org/time#Time) structure so you can access its fields: + +```go-html-template +{{ time "2016-05-28" }} → "2016-05-28T00:00:00Z" +{{ (time "2016-05-28").YearDay }} → 149 +{{ mul 1000 (time "2016-05-28T10:30:00.00+10:00").Unix }} → 1464395400000, or Unix time in milliseconds +``` + +## Using locations + +The optional `TIMEZONE` argument is a string that sets a default time zone (or more specific, the location, which represents the collection of time offsets in a geographical area) that is associated with the specified time value. If the time value has an explicit timezone or offset specified, it will take precedence over the `TIMEZONE` argument. + +The list of valid locations may be system dependent, but should include `UTC`, `Local`, or any location in the [IANA Time Zone database](https://en.wikipedia.org/wiki/List_of_tz_database_time_zones). + +If no `TIMEZONE` is set, the `timeZone` from site configuration will be used. + +```go-html-template +{{ time "2020-10-20" }} → 2020-10-20 00:00:00 +0000 UTC +{{ time "2020-10-20" "America/Los_Angeles" }} → 2020-10-20 00:00:00 -0700 PDT +{{ time "2020-01-20" "America/Los_Angeles" }} → 2020-01-20 00:00:00 -0800 PST +``` + +## Example: Using `time` to get month index + +The following example takes a UNIX timestamp---set as `utimestamp: "1489276800"` in a content's front matter---converts the timestamp (string) to an integer using the [`int` function][int], and then uses [`printf`] to convert the `Month` property of `time` into an index. + +The following example may be useful when setting up [multilingual sites][multilingual]: + +{{< code file="unix-to-month-integer.html" >}} +{{ $time := time (int .Params.addDate)}} +=> $time = 1489276800 +{{ $time.Month }} +=> "March" +{{ $monthindex := printf "%d" $time.Month }} +=> $monthindex = 3 +{{< /code >}} + + +[int]: /functions/cast/toint +[multilingual]: /content-management/multilingual/ +[`printf`]: /functions/fmt/printf diff --git a/content/en/functions/time/Duration.md b/content/en/functions/time/Duration.md new file mode 100644 index 000000000..921f25a96 --- /dev/null +++ b/content/en/functions/time/Duration.md @@ -0,0 +1,46 @@ +--- +title: time.Duration +linkTitle: duration +description: Returns a `time.Duration` structure, using the given time unit and duration number. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [duration] + returnType: time.Duration + signatures: [time.Duration TIME_UNIT DURATION_NUMBER] +relatedFunctions: + - time.AsTime + - time.Duration + - time.Format + - time.Now + - time.ParseDuration +aliases: [/functions/duration] +--- + +`time.Duration` converts a given number into a [`time.Duration`](https://pkg.go.dev/time#Duration) structure so you can access its fields. E.g. you can perform [time operations](https://pkg.go.dev/time#Duration) on the returned `time.Duration` value: + +```go-html-template +{{ printf "There are %.0f seconds in one day." (duration "hour" 24).Seconds }} + +``` + +Make your code simpler to understand by using a [chained pipeline](https://pkg.go.dev/text/template#hdr-Pipelines): + +```go-html-template +{{ mul 7.75 60 | duration "minute" }} → 7h45m0s +{{ mul 120 60 | mul 1000 | duration "millisecond" }} → 2h0m0s +``` + +You have to specify a time unit for the number given to the function. Valid time units are: + +Duration|Valid time units +:--|:-- +hours|`hour`, `h` +minutes|`minute`, `m` +seconds|`second`, `s` +milliseconds|`millisecond`, `ms` +microseconds|`microsecond`, `us`, `µs` +nanoseconds|`nanosecond`, `ns` diff --git a/content/en/functions/time/Format.md b/content/en/functions/time/Format.md new file mode 100644 index 000000000..3a0b1eb2a --- /dev/null +++ b/content/en/functions/time/Format.md @@ -0,0 +1,76 @@ +--- +title: time.Format +description: Returns a formatted and localized time.Time value. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [dateFormat] + returnType: string + signatures: [time.Format LAYOUT INPUT] +relatedFunctions: + - time.AsTime + - time.Duration + - time.Format + - time.Now + - time.ParseDuration +aliases: [/functions/dateformat] +toc: true +--- + +```go-template +{{ $t := "2023-01-27T23:44:58-08:00" }} +{{ $format := "2 Jan 2006" }} + +{{ $t | time.Format $format }} → 27 Jan 2023 + +{{ $t = time.AsTime $t }} +{{ $t | time.Format $format }} → 27 Jan 2023 +``` + +## Layout string + +{{% readfile file="/functions/_common/time-layout-string.md" %}} + +## Localization + +Use the `time.Format` function to localize `time.Time` values for the current language and region. + +{{% note %}} +{{% readfile file="/functions/_common/locales.md" %}} +{{% /note %}} + + +Use the layout string as described above, or one of the tokens below. For example: + +```go-template +{{ .Date | time.Format ":date_medium" }} → Jan 27, 2023 +``` + +Localized to en-US: + +Token|Result +:--|:-- +`:date_full`|`Friday, January 27, 2023` +`:date_long`|`January 27, 2023` +`:date_medium`|`Jan 27, 2023` +`:date_short`|`1/27/23` +`:time_full`|`11:44:58 pm Pacific Standard Time` +`:time_long`|`11:44:58 pm PST` +`:time_medium`|`11:44:58 pm` +`:time_short`|`11:44 pm` + +Localized to de-DE: + +Token|Result +:--|:-- +`:date_full`|`Freitag, 27. Januar 2023` +`:date_long`|`27. Januar 2023` +`:date_medium`|`27.01.2023` +`:date_short`|`27.01.23` +`:time_full`|`23:44:58 Nordamerikanische Westküsten-Normalzeit` +`:time_long`|`23:44:58 PST` +`:time_medium`|`23:44:58` +`:time_short`|`23:44` diff --git a/content/en/functions/time/Now.md b/content/en/functions/time/Now.md new file mode 100644 index 000000000..74b01ecc5 --- /dev/null +++ b/content/en/functions/time/Now.md @@ -0,0 +1,51 @@ +--- +title: time.Now +linkTitle: now +description: Returns the current local time +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [now] + returnType: time.Time + signatures: [time.Now] +relatedFunctions: + - time.AsTime + - time.Duration + - time.Format + - time.Now + - time.ParseDuration +aliases: [/functions/now] +--- + +See [`time.Time`](https://godoc.org/time#Time). + +For example, building your site on June 24, 2017, with the following templating: + +```go-html-template +
+ © {{ now.Format "2006" }} +
+``` + +would produce the following: + +```html +
+ © 2017 +
+``` + +The above example uses the [`.Format` function](/functions/format), which page includes a full listing of date formatting using Go's layout string. + +{{% note %}} +Older Hugo themes may still be using the obsolete Page’s `.Now` (uppercase with leading dot), which causes build error that looks like the following: + + ERROR ... Error while rendering "..." in "...": ... + executing "..." at <.Now.Format>: + can't evaluate field Now in type *hugolib.PageOutput + +Be sure to use `now` (lowercase with _**no**_ leading dot) in your templating. +{{% /note %}} diff --git a/content/en/functions/time/ParseDuration.md b/content/en/functions/time/ParseDuration.md new file mode 100644 index 000000000..e3abc7c15 --- /dev/null +++ b/content/en/functions/time/ParseDuration.md @@ -0,0 +1,30 @@ +--- +title: time.ParseDuration +description: Parses a given duration string into a `time.Duration` structure. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: time.Duration + signatures: [time.ParseDuration DURATION] +relatedFunctions: + - time.AsTime + - time.Duration + - time.Format + - time.Now + - time.ParseDuration +aliases: [/functions/time.parseduration] +--- + +`time.ParseDuration` parses a duration string into a [`time.Duration`](https://pkg.go.dev/time#Duration) structure so you can access its fields. +A duration string is a possibly signed sequence of decimal numbers, each with optional fraction and a unit suffix, such as `300ms`, `-1.5h` or `2h45m`. Valid time units are `ns`, `us` (or `µs`), `ms`, `s`, `m`, `h`. + +You can perform [time operations](https://pkg.go.dev/time#Duration) on the returned `time.Duration` value: + +```go-html-template +{{ printf "There are %.0f seconds in one day." (time.ParseDuration "24h").Seconds }} + +``` diff --git a/content/en/functions/title.md b/content/en/functions/title.md deleted file mode 100644 index d8e0f73a4..000000000 --- a/content/en/functions/title.md +++ /dev/null @@ -1,23 +0,0 @@ ---- -title: title -description: Converts the provided string to title case. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: - - "title STRING" - - "strings.Title STRING" -relatedfuncs: [] ---- - -```go-html-template -{{ title "table of contents (TOC)" }} → "Table of Contents (TOC)" -``` - -By default, Hugo adheres to the capitalization rules in the [Associated Press (AP) Stylebook]. Change your [site configuration] if you would prefer to follow the [Chicago Manual of Style], or to use Go's convention of capitalizing every word. - -[Associated Press (AP) Stylebook]: https://www.apstylebook.com/ -[Chicago Manual of Style]: https://www.chicagomanualofstyle.org/home.html -[site configuration]: /getting-started/configuration/#configure-title-case diff --git a/content/en/functions/transform.Remarshal.md b/content/en/functions/transform.Remarshal.md deleted file mode 100644 index e1605197f..000000000 --- a/content/en/functions/transform.Remarshal.md +++ /dev/null @@ -1,88 +0,0 @@ ---- -title: transform.Remarshal -description: Marshals a string of serialized data, or a map, into a string of serialized data in the specified format. -categories: [functions] -menu: - docs: - parent: functions -keywords: [] -signature: [ transform.Remarshal FORMAT INPUT ] ---- - -The FORMAT must be one of `json`, `toml`, `yaml`, or `xml`. If the INPUT is a string of serialized data, it must be valid JSON, TOML, YAML, or XML. - -{{% note %}} -This function is primarily a helper for Hugo's documentation, used to convert configuration and front matter examples to JSON, TOML, and YAML. - -This is not a general purpose converter, and may change without notice if required for Hugo's documentation site. -{{% /note %}} - -Example 1 -: Convert a string of TOML to JSON. - -```go-html-template -{{ $s := ` - baseURL = 'https://example.org/' - languageCode = 'en-US' - title = 'ABC Widgets' -`}} -
{{ transform.Remarshal "json" $s }}
-``` - -Resulting HTML: - -```html -
{
-   "baseURL": "https://example.org/",
-   "languageCode": "en-US",
-   "title": "ABC Widgets"
-}
-
-``` - -Rendered in browser: - -```text -{ - "baseURL": "https://example.org/", - "languageCode": "en-US", - "title": "ABC Widgets" -} -``` - -Example 2 -: Convert a map to YAML. - -```go-html-template -{{ $m := dict - "a" "Hugo rocks!" - "b" (dict "question" "What is 6x7?" "answer" 42) - "c" (slice "foo" "bar") -}} -
{{ transform.Remarshal "yaml" $m }}
-``` - -Resulting HTML: - -```html -
a: Hugo rocks!
-b:
-  answer: 42
-  question: What is 6x7?
-c:
-- foo
-- bar
-
-``` - -Rendered in browser: - -```text -a: Hugo rocks! -b: - answer: 42 - question: What is 6x7? -c: -- foo -- bar -``` diff --git a/content/en/functions/transform.Unmarshal.md b/content/en/functions/transform.Unmarshal.md deleted file mode 100644 index 7d0920da8..000000000 --- a/content/en/functions/transform.Unmarshal.md +++ /dev/null @@ -1,73 +0,0 @@ ---- -title: transform.Unmarshal -description: "`transform.Unmarshal` (alias `unmarshal`) parses the input and converts it into a map or an array. Supported formats are JSON, TOML, YAML, XML and CSV." -categories: [functions] -menu: - docs: - parent: functions -keywords: [] -signature: ["RESOURCE or STRING | transform.Unmarshal [OPTIONS]"] ---- - -The function accepts either a `Resource` created in [Hugo Pipes](/hugo-pipes/) or via [Page Bundles](/content-management/page-bundles/), or simply a string. The two examples below will produce the same map: - -```go-html-template -{{ $greetings := "hello = \"Hello Hugo\"" | transform.Unmarshal }}` -``` - -```go-html-template -{{ $greetings := "hello = \"Hello Hugo\"" | resources.FromString "data/greetings.toml" | transform.Unmarshal }} -``` - -In both the above examples, you get a map you can work with: - -```go-html-template -{{ $greetings.hello }} -``` - -The above prints `Hello Hugo`. - -## CSV options - -Unmarshal with CSV as input has some options you can set: - -delimiter -: The delimiter used, default is `,`. - -comment -: The comment character used in the CSV. If set, lines beginning with the comment character without preceding whitespace are ignored.: - -Example: - -```go-html-template -{{ $csv := "a;b;c" | transform.Unmarshal (dict "delimiter" ";") }} -``` - -## XML data - -As a convenience, Hugo allows you to access XML data in the same way that you access JSON, TOML, and YAML: you do not need to specify the root node when accessing the data. - -To get the contents of `` in the document below, you use `{{ .message.title }}`: - -```xml -<root> - <message> - <title>Hugo rocks! - Thanks for using Hugo - - -``` - -The following example lists the items of an RSS feed: - -```go-html-template -{{ with resources.GetRemote "https://example.com/rss.xml" | transform.Unmarshal }} - {{ range .channel.item }} - {{ .title | plainify | htmlUnescape }}
-

{{ .description | plainify | htmlUnescape }}

- {{ $link := .link | plainify | htmlUnescape }} - {{ $link }}
-
- {{ end }} -{{ end }} -``` diff --git a/content/en/functions/transform/CanHighlight.md b/content/en/functions/transform/CanHighlight.md new file mode 100644 index 000000000..eabef933b --- /dev/null +++ b/content/en/functions/transform/CanHighlight.md @@ -0,0 +1,22 @@ +--- +title: transform.CanHighlight +description: Reports whether the given code language is supported by the Chroma highlighter. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: bool + signatures: [transform.CanHighlight LANGUAGE] +relatedFunctions: + - transform.CanHighlight + - transform.Highlight + - transform.HighlightCodeBlock +--- + +```go-html-template +{{ transform.CanHighlight "go" }} → true +{{ transform.CanHighlight "klingon" }} → false +``` diff --git a/content/en/functions/transform/Emojify.md b/content/en/functions/transform/Emojify.md new file mode 100644 index 000000000..324c41851 --- /dev/null +++ b/content/en/functions/transform/Emojify.md @@ -0,0 +1,31 @@ +--- +title: transform.Emojify +linkTitle: emojify +description: Runs a string through the Emoji emoticons processor. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [emojify] + returnType: template.HTML + signatures: [transform.Emojify INPUT] +namespace: transform +relatedFunctions: [] +aliases: [/functions/emojify] +--- + +`emojify` runs a passed string through the Emoji emoticons processor. + +See the [Emoji cheat sheet][emojis] for available emoticons. + +The `emojify` function can be called in your templates but not directly in your content files by default. For emojis in content files, set `enableEmoji` to `true` in your site's [configuration]. Then you can write emoji shorthand directly into your content files; e.g. I :heart: Hugo!: + +I :heart: Hugo! + + +[configuration]: /getting-started/configuration/ +[emojis]: https://www.webfx.com/tools/emoji-cheat-sheet/ +[sc]: /templates/shortcode-templates/ +[scsource]: https://github.com/gohugoio/hugo/tree/master/docs/layouts/shortcodes diff --git a/content/en/functions/transform/HTMLEscape.md b/content/en/functions/transform/HTMLEscape.md new file mode 100644 index 000000000..62249367b --- /dev/null +++ b/content/en/functions/transform/HTMLEscape.md @@ -0,0 +1,24 @@ +--- +title: transform.HTMLEscape +linkTitle: htmlEscape +description: Returns the given string with the reserved HTML codes escaped. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [htmlEscape] + returnType: string + signatures: [transform.HTMLEscape INPUT] +relatedFunctions: + - transform.HTMLEscape + - transform.HTMLUnescape +aliases: [/functions/htmlescape] +--- + +In the result `&` becomes `&` and so on. It escapes only: `<`, `>`, `&`, `'` and `"`. + +```go-html-template +{{ htmlEscape "Hugo & Caddy > WordPress & Apache" }} → "Hugo & Caddy > WordPress & Apache" +``` diff --git a/content/en/functions/transform/HTMLUnescape.md b/content/en/functions/transform/HTMLUnescape.md new file mode 100644 index 000000000..c0774232f --- /dev/null +++ b/content/en/functions/transform/HTMLUnescape.md @@ -0,0 +1,24 @@ +--- +title: transform.HTMLUnescape +linkTitle: htmlUnescape +description: Returns the given string with HTML escape codes un-escaped. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [htmlUnescape] + returnType: string + signatures: [transform.HTMLUnescape INPUT] +relatedFunctions: + - transform.HTMLEscape + - transform.HTMLUnescape +aliases: [/functions/htmlunescape] +--- + +Remember to pass the output of this to `safeHTML` if fully un-escaped characters are desired. Otherwise, the output will be escaped again as normal. + +```go-html-template +{{ htmlUnescape "Hugo & Caddy > WordPress & Apache" }} → "Hugo & Caddy > WordPress & Apache" +``` diff --git a/content/en/functions/transform/Highlight.md b/content/en/functions/transform/Highlight.md new file mode 100644 index 000000000..93043b4a1 --- /dev/null +++ b/content/en/functions/transform/Highlight.md @@ -0,0 +1,113 @@ +--- +title: transform.Highlight +linkTitle: highlight +description: Renders code with a syntax highlighter. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [highlight] + returnType: template.HTML + signatures: ['transform.Highlight INPUT LANG [OPTIONS]'] +namespace: transform +relatedFunctions: + - transform.CanHighlight + - transform.Highlight + - transform.HighlightCodeBlock +aliases: [/functions/highlight] +toc: true +--- + +The `highlight` function uses the [Chroma] syntax highlighter, supporting over 200 languages with more than 40 available styles. + +## Arguments + +INPUT +: The code to highlight. + +LANG +: The language of the code to highlight. Choose from one of the [supported languages]. Case-insensitive. + +OPTIONS +: An optional, comma-separated list of zero or more [options]. Set default values in [site configuration]. + +## Options + +lineNos +: Boolean. Default is `false`.\ +Display a number at the beginning of each line. + +lineNumbersInTable +: Boolean. Default is `true`.\ +Render the highlighted code in an HTML table with two cells. The left table cell contains the line numbers. The right table cell contains the code, allowing a user to select and copy the code without line numbers. Irrelevant if `lineNos` is `false`. + +anchorLineNos +: Boolean. Default is `false`.\ +Render each line number as an HTML anchor element, and set the `id` attribute of the surrounding `` to the line number. Irrelevant if `lineNos` is `false`. + +lineAnchors +: String. Default is `""`.\ +When rendering a line number as an HTML anchor element, prepend this value to the `id` attribute of the surrounding ``. This provides unique `id` attributes when a page contains two or more code blocks. Irrelevant if `lineNos` or `anchorLineNos` is `false`. + +lineNoStart +: Integer. Default is `1`.\ +The number to display at the beginning of the first line. Irrelevant if `lineNos` is `false`. + +hl_Lines +: String. Default is `""`.\ +A space-separated list of lines to emphasize within the highlighted code. To emphasize lines 2, 3, 4, and 7, set this value to `2-4 7`. This option is independent of the `lineNoStart` option. + +hl_inline +: Boolean. Default is `false`.\ +Render the highlighted code without a wrapping container. + +style +: String. Default is `monokai`.\ +The CSS styles to apply to the highlighted code. See the [style gallery] for examples. Case-sensitive. + +noClasses +: Boolean. Default is `true`.\ +Use inline CSS styles instead of an external CSS file. To use an external CSS file, set this value to `false` and [generate the file with the hugo client][hugo client]. + +tabWidth +: Integer. Default is `4`.\ +Substitute this number of spaces for each tab character in your highlighted code. Irrelevant if `noClasses` is `false`. + +guessSyntax +: Boolean. Default is `false`.\ +If the `LANG` argument is blank or an unrecognized language, auto-detect the language if possible, otherwise use a fallback language. + +{{% note %}} +Instead of specifying both `lineNos` and `lineNumbersInTable`, you can use the following shorthand notation: + +`lineNos=inline` +: equivalent to `lineNos=true` and `lineNumbersInTable=false` + +`lineNos=table` +: equivalent to `lineNos=true` and `lineNumbersInTable=true` +{{% /note %}} + +## Examples + +```go-html-template +{{ $input := `fmt.Println("Hello World!")` }} +{{ transform.Highlight $input "go" }} + +{{ $input := `console.log('Hello World!');` }} +{{ $lang := "js" }} +{{ transform.Highlight $input $lang "lineNos=table, style=api" }} + +{{ $input := `echo "Hello World!"` }} +{{ $lang := "bash" }} +{{ $options := dict "lineNos" "table" "style" "dracula" }} +{{ transform.Highlight $input $lang $options }} +``` + +[Chroma]: https://github.com/alecthomas/chroma +[hugo client]: /commands/hugo_gen_chromastyles +[options]: #options +[site configuration]: /getting-started/configuration-markup#highlight +[style gallery]: https://xyproto.github.io/splash/docs/ +[supported languages]: /content-management/syntax-highlighting#list-of-chroma-highlighting-languages diff --git a/content/en/functions/transform/HighlightCodeBlock.md b/content/en/functions/transform/HighlightCodeBlock.md new file mode 100644 index 000000000..fa7045641 --- /dev/null +++ b/content/en/functions/transform/HighlightCodeBlock.md @@ -0,0 +1,43 @@ +--- +title: transform.HighlightCodeBlock +description: Highlights code received in context within a code block render hook. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: highlight.HighlightResult + signatures: ['transform.HighlightCodeBlock CONTEXT [OPTIONS]'] +relatedFunctions: + - transform.CanHighlight + - transform.Highlight + - transform.HighlightCodeBlock +--- + +This function is only useful within a code block render hook. + +Given the context passed into a code block render hook, `transform.HighlightCodeBlock` returns a `HighlightResult` object with two methods. + +.Wrapped +: (`template.HTML`) Returns highlighted code wrapped in `
`, `
`, and `` elements. This is identical to the value returned by the transform.Highlight function.
+
+.Inner
+: (`template.HTML`) Returns highlighted code without any wrapping elements, allowing you to create your own wrapper.
+
+
+```go-html-template
+{{ $result := transform.HighlightCodeBlock . }}
+{{ $result.Wrapped }}
+```
+
+To override the default [highlighting options]:
+
+```go-html-template
+{{ $options := merge .Options (dict "linenos" true) }}
+{{ $result := transform.HighlightCodeBlock . $options }}
+{{ $result.Wrapped }}
+```
+
+[highlighting options]: /functions/transform/highlight/#options
diff --git a/content/en/functions/transform/Markdownify.md b/content/en/functions/transform/Markdownify.md
new file mode 100644
index 000000000..b0be902ce
--- /dev/null
+++ b/content/en/functions/transform/Markdownify.md
@@ -0,0 +1,35 @@
+---
+title: transform.Markdownify
+linkTitle: markdownify
+description: Renders markdown to HTML.
+categories: [functions]
+keywords: []
+menu:
+  docs:
+    parent: functions
+function:
+  aliases: [markdownify]
+  returnType: template.HTML
+  signatures: [transform.Markdownify INPUT]
+relatedFunctions: []
+aliases: [/functions/markdownify]
+---
+
+```go-html-template
+{{ .Title | markdownify }}
+```
+
+If the resulting HTML is a single paragraph, Hugo removes the wrapping `p` tags to produce inline HTML as required per the example above.
+
+To keep the wrapping `p` tags for a single paragraph, use the [`.Page.RenderString`] method, setting the `display` option to `block`.
+
+If the resulting HTML is two or more paragraphs, Hugo leaves the wrapping `p` tags in place.
+
+[`.Page.RenderString`]: /functions/renderstring/
+
+{{% note %}}
+Although the `markdownify` function honors [markdown render hooks] when rendering markdown to HTML, use the `.Page.RenderString` method instead of `markdownify` if a render hook accesses `.Page` context. See issue [#9692] for details.
+
+[markdown render hooks]: /templates/render-hooks/
+[#9692]: https://github.com/gohugoio/hugo/issues/9692
+{{% /note %}}
diff --git a/content/en/functions/transform/Plainify.md b/content/en/functions/transform/Plainify.md
new file mode 100644
index 000000000..163233d4a
--- /dev/null
+++ b/content/en/functions/transform/Plainify.md
@@ -0,0 +1,24 @@
+---
+title: transform.Plainify
+linkTitle: plainify
+description: Returns a string with all HTML tags removed.
+categories: [functions]
+keywords: []
+menu:
+  docs:
+    parent: functions
+function:
+  aliases: [plainify]
+  returnType: string
+  signatures: [transform.Plainify INPUT]
+relatedFunctions: []
+aliases: [/functions/plainify]
+---
+
+```go-html-template
+{{ "BatMan" | plainify }} → "BatMan"
+```
+
+See also the `.PlainWords`, `.Plain`, and `.RawContent` [page variables][pagevars].
+
+[pagevars]: /variables/page/
diff --git a/content/en/functions/transform/Remarshal.md b/content/en/functions/transform/Remarshal.md
new file mode 100644
index 000000000..8f6e58247
--- /dev/null
+++ b/content/en/functions/transform/Remarshal.md
@@ -0,0 +1,96 @@
+---
+title: transform.Remarshal
+description: Marshals a string of serialized data, or a map, into a string of serialized data in the specified format.
+categories: [functions]
+keywords: []
+menu:
+  docs:
+    parent: functions
+function:
+  aliases: []
+  returnType: string
+  signatures: [transform.Remarshal FORMAT INPUT]
+relatedFunctions:
+  - encoding.Jsonify
+  - transform.Remarshal
+  - transform.Unmarshal
+aliases: [/functions/transform.remarshal]
+---
+
+The FORMAT must be one of `json`, `toml`, `yaml`, or `xml`. If the INPUT is a string of serialized data, it must be valid JSON, TOML, YAML, or XML.
+
+{{% note %}}
+This function is primarily a helper for Hugo's documentation, used to convert configuration and front matter examples to JSON, TOML, and YAML.
+
+This is not a general purpose converter, and may change without notice if required for Hugo's documentation site.
+{{% /note %}}
+
+Example 1
+: Convert a string of TOML to JSON.
+
+```go-html-template
+{{ $s := `
+  baseURL = 'https://example.org/'
+  languageCode = 'en-US'
+  title = 'ABC Widgets'
+`}}
+
{{ transform.Remarshal "json" $s }}
+``` + +Resulting HTML: + +```html +
{
+   "baseURL": "https://example.org/",
+   "languageCode": "en-US",
+   "title": "ABC Widgets"
+}
+
+``` + +Rendered in browser: + +```text +{ + "baseURL": "https://example.org/", + "languageCode": "en-US", + "title": "ABC Widgets" +} +``` + +Example 2 +: Convert a map to YAML. + +```go-html-template +{{ $m := dict + "a" "Hugo rocks!" + "b" (dict "question" "What is 6x7?" "answer" 42) + "c" (slice "foo" "bar") +}} +
{{ transform.Remarshal "yaml" $m }}
+``` + +Resulting HTML: + +```html +
a: Hugo rocks!
+b:
+  answer: 42
+  question: What is 6x7?
+c:
+- foo
+- bar
+
+``` + +Rendered in browser: + +```text +a: Hugo rocks! +b: + answer: 42 + question: What is 6x7? +c: +- foo +- bar +``` diff --git a/content/en/functions/transform/Unmarshal.md b/content/en/functions/transform/Unmarshal.md new file mode 100644 index 000000000..ab32d13de --- /dev/null +++ b/content/en/functions/transform/Unmarshal.md @@ -0,0 +1,83 @@ +--- +title: transform.Unmarshal +description: Parses the input and converts it into a map or an array. Supported formats are JSON, TOML, YAML, XML and CSV. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [unmarshal] + returnType: any + signatures: + - RESOURCE or STRING | transform.Unmarshal [OPTIONS] + - RESOURCE or STRING | unmarshal [OPTIONS] +relatedFunctions: + - encoding.Jsonify + - transform.Remarshal + - transform.Unmarshal +aliases: [/functions/transform.unmarshal] +--- + +The function accepts either a `Resource` created in [Hugo Pipes](/hugo-pipes/) or via [Page Bundles](/content-management/page-bundles/), or simply a string. The two examples below will produce the same map: + +```go-html-template +{{ $greetings := "hello = \"Hello Hugo\"" | transform.Unmarshal }}` +``` + +```go-html-template +{{ $greetings := "hello = \"Hello Hugo\"" | resources.FromString "data/greetings.toml" | transform.Unmarshal }} +``` + +In both the above examples, you get a map you can work with: + +```go-html-template +{{ $greetings.hello }} +``` + +The above prints `Hello Hugo`. + +## CSV options + +Unmarshal with CSV as input has some options you can set: + +delimiter +: The delimiter used, default is `,`. + +comment +: The comment character used in the CSV. If set, lines beginning with the comment character without preceding whitespace are ignored.: + +Example: + +```go-html-template +{{ $csv := "a;b;c" | transform.Unmarshal (dict "delimiter" ";") }} +``` + +## XML data + +As a convenience, Hugo allows you to access XML data in the same way that you access JSON, TOML, and YAML: you do not need to specify the root node when accessing the data. + +To get the contents of `` in the document below, you use `{{ .message.title }}`: + +```xml +<root> + <message> + <title>Hugo rocks! + Thanks for using Hugo + + +``` + +The following example lists the items of an RSS feed: + +```go-html-template +{{ with resources.GetRemote "https://example.com/rss.xml" | transform.Unmarshal }} + {{ range .channel.item }} + {{ .title | plainify | htmlUnescape }}
+

{{ .description | plainify | htmlUnescape }}

+ {{ $link := .link | plainify | htmlUnescape }} + {{ $link }}
+
+ {{ end }} +{{ end }} +``` diff --git a/content/en/functions/trim.md b/content/en/functions/trim.md deleted file mode 100644 index 3d664abea..000000000 --- a/content/en/functions/trim.md +++ /dev/null @@ -1,36 +0,0 @@ ---- -title: trim -description: Returns a slice of a passed string with all leading and trailing characters from cutset removed. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: - - "trim INPUT CUTSET" - - "strings.Trim INPUT CUTSET" -relatedfuncs: [] ---- - -```go-html-template -{{ trim "++Batman--" "+-" }} → "Batman" -``` - -`trim` *requires* the second argument, which tells the function specifically what to remove from the first argument. There is no default value for the second argument, so **the following usage will not work**: - -```go-html-template -{{ trim .Inner }} -``` - -Instead, the following example tells `trim` to remove extra new lines from the content contained in the [shortcode `.Inner` variable][shortcodevars]: - -```go-html-template -{{ trim .Inner "\n" }} -``` - -{{% note %}} -Go templates also provide a simple [method for trimming whitespace](/templates/introduction/#whitespace) from either side of a Go tag by including a hyphen (`-`). -{{% /note %}} - - -[shortcodevars]: /variables/shortcodes/ diff --git a/content/en/functions/truncate.md b/content/en/functions/truncate.md deleted file mode 100644 index cf38a2dfd..000000000 --- a/content/en/functions/truncate.md +++ /dev/null @@ -1,23 +0,0 @@ ---- -title: truncate -description: Truncates a text to a max length without cutting words or leaving unclosed HTML tags. -categories: [functions] -menu: - docs: - parent: functions -keywords: [strings] -signature: - - "truncate SIZE [ELLIPSIS] INPUT" - - "strings.Truncate SIZE [ELLIPSIS] INPUT" -relatedfuncs: [] ---- - -Since Go templates are HTML-aware, `truncate` will intelligently handle normal strings vs HTML strings: - -```go-html-template -{{ "Keep my HTML" | safeHTML | truncate 10 }}` → Keep my …` -``` - -{{% note %}} -If you have a raw string that contains HTML tags you want to remain treated as HTML, you will need to convert the string to HTML using the [`safeHTML` template function](/functions/safehtml) before sending the value to truncate. Otherwise, the HTML tags will be escaped when passed through the `truncate` function. -{{% /note %}} diff --git a/content/en/functions/union.md b/content/en/functions/union.md deleted file mode 100644 index 86a874c91..000000000 --- a/content/en/functions/union.md +++ /dev/null @@ -1,41 +0,0 @@ ---- -title: union -description: Given two arrays or slices, returns a new array that contains the elements or objects that belong to either or both arrays/slices. -categories: [functions] -menu: - docs: - parent: functions -keywords: [collections,intersect,union,complement] -signature: ["union SET1 SET2"] -relatedfuncs: [intersect,where] ---- - -Given two arrays (or slices) A and B, this function will return a new array that contains the elements or objects that belong to either A or to B or to both. The elements supported are strings, integers, and floats (only float64). - -```go-html-template -{{ union (slice 1 2 3) (slice 3 4 5) }} - - -{{ union (slice 1 2 3) nil }} - - -{{ union nil (slice 1 2 3) }} - - -{{ union nil nil }} - -``` - -## OR filter in where query - -This is also very useful to use as `OR` filters when combined with where: - -```go-html-template -{{ $pages := where .Site.RegularPages "Type" "not in" (slice "page" "about") }} -{{ $pages = $pages | union (where .Site.RegularPages "Params.pinned" true) }} -{{ $pages = $pages | intersect (where .Site.RegularPages "Params.images" "!=" nil) }} -``` - -The above fetches regular pages not of `page` or `about` type unless they are pinned. And finally, we exclude all pages with no `images` set in Page parameters. - -See [intersect](/functions/intersect) for `AND`. diff --git a/content/en/functions/uniq.md b/content/en/functions/uniq.md deleted file mode 100644 index aecdccf95..000000000 --- a/content/en/functions/uniq.md +++ /dev/null @@ -1,15 +0,0 @@ ---- -title: uniq -description: Takes in a slice or array and returns a slice with duplicate elements removed. -categories: [functions] -menu: - docs: - parent: functions -keywords: [multilingual,i18n,urls] -signature: [uniq SET] ---- - - -```go-html-template -{{ slice 1 3 2 1 | uniq }} → [1 3 2] -``` diff --git a/content/en/functions/unix.md b/content/en/functions/unix.md deleted file mode 100644 index 60fae9248..000000000 --- a/content/en/functions/unix.md +++ /dev/null @@ -1,30 +0,0 @@ ---- -title: .Unix -description: Converts a time.Time value to the number of seconds elapsed since the Unix epoch, excluding leap seconds. The Unix epoch is 00:00:00 UTC on 1 January 1970. -keywords: [dates,time] -categories: [functions] -menu: - docs: - parent: functions -signature: [".Unix",".UnixMilli",".UnixMicro",".UnixNano"] -relatedfuncs: [Format,dateFormat,now,time] ---- - -The `Milli`, `Micro`, and `Nano` variants return the number of milliseconds, microseconds, and nanoseconds (respectively) elapsed since the Unix epoch. - -```go-html-template -.Date.Unix --> 1637259694 -.ExpiryDate.Unix --> 1672559999 -.Lastmod.Unix --> 1637361786 -.PublishDate.Unix --> 1637421261 - -("1970-01-01T00:00:00-00:00" | time.AsTime).Unix --> 0 -("1970-01-01T00:00:42-00:00" | time.AsTime).Unix --> 42 -("1970-04-11T01:48:29-08:00" | time.AsTime).Unix --> 8675309 -("2026-05-02T20:09:31-07:00" | time.AsTime).Unix --> 1777777771 - -now.Unix --> 1637447841 -now.UnixMilli --> 1637447841347 -now.UnixMicro --> 1637447841347378 -now.UnixNano --> 1637447841347378799 -``` diff --git a/content/en/functions/upper.md b/content/en/functions/upper.md deleted file mode 100644 index e11065f79..000000000 --- a/content/en/functions/upper.md +++ /dev/null @@ -1,21 +0,0 @@ ---- -title: upper -description: Converts all characters in a string to uppercase -keywords: [] -categories: [functions] -menu: - docs: - parent: functions -toc: -signature: - - "upper INPUT" - - "strings.ToUpper INPUT" -relatedfuncs: [] ---- - -Note that `upper` can be applied in your templates in more than one way: - -```go-html-template -{{ upper "BatMan" }} → "BATMAN" -{{ "BatMan" | upper }} → "BATMAN" -``` diff --git a/content/en/functions/urlize.md b/content/en/functions/urlize.md deleted file mode 100644 index 7a9cf25e8..000000000 --- a/content/en/functions/urlize.md +++ /dev/null @@ -1,62 +0,0 @@ ---- -title: urlize -description: Takes a string, sanitizes it for usage in URLs, and converts spaces to hyphens. -categories: [functions] -menu: - docs: - parent: functions -keywords: [urls,strings] -signature: ["urlize INPUT"] -relatedfuncs: [] ---- - -The following examples pull from a content file with the following front matter: - -{{< code-toggle file="content/blog/greatest-city.md" fm=true copy=false >}} -title = "The World's Greatest City" -location = "Chicago IL" -tags = ["pizza","beer","hot dogs"] -{{< /code-toggle >}} - -The following might be used as a partial within a [single page template][singletemplate]: - -{{< code file="layouts/partials/content-header.html" >}} -
-

{{ .Title }}

- {{ with .Params.location }} - - {{ end }} - - {{ with .Params.tags }} -
    - {{ range .}} -
  • - {{ . }} -
  • - {{ end }} -
- {{ end }} -
-{{< /code >}} - -The preceding partial would then output to the rendered page as follows: - -```html -
-

The World's Greatest City

- - -
-``` - -[singletemplate]: /templates/single-page-templates/ diff --git a/content/en/functions/urlquery.md b/content/en/functions/urlquery.md deleted file mode 100644 index 11ada38c4..000000000 --- a/content/en/functions/urlquery.md +++ /dev/null @@ -1,25 +0,0 @@ ---- -title: urlquery -description: Returns the escaped value of the textual representation of its arguments in a form suitable for embedding in a URL query. -categories: [functions] -menu: - docs: - parent: functions -keywords: [urls] -signature: ["urlquery INPUT [INPUT]..."] -relatedfuncs: [] ---- - - -This template code: - -```go-html-template -{{ $u := urlquery "https://" "example.com" | safeURL }} -Link -``` - -Is rendered to: - -```html -Link -``` diff --git a/content/en/functions/urls.JoinPath.md b/content/en/functions/urls.JoinPath.md deleted file mode 100644 index f11632367..000000000 --- a/content/en/functions/urls.JoinPath.md +++ /dev/null @@ -1,25 +0,0 @@ ---- -title: urls.JoinPath -description: Joins the provided elements into a URL string and cleans the result of any ./ or ../ elements. If the argument list is empty, JoinPath returns an empty string. -categories: [functions] -menu: - docs: - parent: functions -keywords: [urls,path,join] -signature: ["urls.JoinPath ELEMENT..."] ---- - -```go-html-template -{{ urls.JoinPath }} → "" -{{ urls.JoinPath "" }} → "/" -{{ urls.JoinPath "a" }} → "a" -{{ urls.JoinPath "a" "b" }} → "a/b" -{{ urls.JoinPath "/a" "b" }} → "/a/b" -{{ urls.JoinPath "https://example.org" "b" }} → "https://example.org/b" - -{{ urls.JoinPath (slice "a" "b") }} → "a/b" -``` - -Unlike the [`path.Join`] function, `urls.JoinPath` retains consecutive leading slashes. - -[`path.Join`]: /functions/path.join/ diff --git a/content/en/functions/urls.Parse.md b/content/en/functions/urls.Parse.md deleted file mode 100644 index b2d781e7f..000000000 --- a/content/en/functions/urls.Parse.md +++ /dev/null @@ -1,32 +0,0 @@ ---- -title: urls.Parse -description: Parses a URL into a URL structure. -categories: [functions] -menu: - docs: - parent: functions -keywords: [urls] -signature: ["urls.Parse URL"] ---- - -The `urls.Parse` function parses a URL into a [URL structure](https://godoc.org/net/url#URL). The URL may be relative (a path, without a host) or absolute (starting with a [scheme]). Hugo throws an error when parsing an invalid URL. - -[scheme]: https://www.iana.org/assignments/uri-schemes/uri-schemes.xhtml#uri-schemes-1 - - -```go-html-template -{{ $url := "https://example.org:123/foo?a=6&b=7#bar" }} -{{ $u := urls.Parse $url }} - -{{ $u.IsAbs }} → true -{{ $u.Scheme }} → https -{{ $u.Host }} → example.org:123 -{{ $u.Hostname }} → example.org -{{ $u.RequestURI }} → /foo?a=6&b=7 -{{ $u.Path }} → /foo -{{ $u.Query }} → map[a:[6] b:[7]] -{{ $u.Query.a }} → [6] -{{ $u.Query.Get "a" }} → 6 -{{ $u.Query.Has "b" }} → true -{{ $u.Fragment }} → bar -``` diff --git a/content/en/functions/urls/AbsLangURL.md b/content/en/functions/urls/AbsLangURL.md new file mode 100644 index 000000000..ad73bbff0 --- /dev/null +++ b/content/en/functions/urls/AbsLangURL.md @@ -0,0 +1,72 @@ +--- +title: urls.AbsLangURL +linkTitle: absLangURL +description: Returns an absolute URL with a language prefix, if any. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [absLangURL] + returnType: template.HTML + signatures: [urls.AbsLangURL INPUT] +relatedFunctions: + - urls.AbsLangURL + - urls.AbsURL + - urls.RelLangURL + - urls.RelURL +aliases: [/functions/abslangurl] +--- + +Use this function with both monolingual and multilingual configurations. The URL returned by this function depends on: + +- Whether the input begins with a slash +- The `baseURL` in site configuration +- The language prefix, if any + +In examples that follow, the project is multilingual with content in both Español (`es`) and English (`en`). The default language is Español. The returned values are from the English site. + +### Input does not begin with a slash + +If the input does not begin with a slash, the resulting URL will be correct regardless of the `baseURL`. + +With `baseURL = https://example.org/` + +```go-html-template +{{ absLangURL "" }} → https://example.org/en/ +{{ absLangURL "articles" }} → https://example.org/en/articles +{{ absLangURL "style.css" }} → https://example.org/en/style.css +``` + +With `baseURL = https://example.org/docs/` + +```go-html-template +{{ absLangURL "" }} → https://example.org/docs/en/ +{{ absLangURL "articles" }} → https://example.org/docs/en/articles +{{ absLangURL "style.css" }} → https://example.org/docs/en/style.css +``` + +### Input begins with a slash + +If the input begins with a slash, the resulting URL will be incorrect when the `baseURL` includes a subdirectory. With a leading slash, the function returns a URL relative to the protocol+host section of the `baseURL`. + +With `baseURL = https://example.org/` + +```go-html-template +{{ absLangURL "/" }} → https://example.org/en/ +{{ absLangURL "/articles" }} → https://example.org/en/articles +{{ absLangURL "/style.css" }} → https://example.org/en/style.css +``` + +With `baseURL = https://example.org/docs/` + +```go-html-template +{{ absLangURL "/" }} → https://example.org/en/ +{{ absLangURL "/articles" }} → https://example.org/en/articles +{{ absLangURL "/style.css" }} → https://example.org/en/style.css +``` + +{{% note %}} +The last three examples are not desirable in most situations. As a best practice, never include a leading slash when using this function. +{{% /note %}} diff --git a/content/en/functions/urls/AbsURL.md b/content/en/functions/urls/AbsURL.md new file mode 100644 index 000000000..bb6816f57 --- /dev/null +++ b/content/en/functions/urls/AbsURL.md @@ -0,0 +1,71 @@ +--- +title: urls.AbsURL +linkTitle: absURL +description: Returns an absolute URL. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [absURL] + returnType: template.html + signatures: [urls.AbsURL INPUT] +relatedFunctions: + - urls.AbsLangURL + - urls.AbsURL + - urls.RelLangURL + - urls.RelURL +aliases: [/functions/absurl] +--- + +With multilingual configurations, use the [`absLangURL`] function instead. The URL returned by this function depends on: + +- Whether the input begins with a slash +- The `baseURL` in site configuration + +### Input does not begin with a slash + +If the input does not begin with a slash, the resulting URL will be correct regardless of the `baseURL`. + +With `baseURL = https://example.org/` + +```go-html-template +{{ absURL "" }} → https://example.org/ +{{ absURL "articles" }} → https://example.org/articles +{{ absURL "style.css" }} → https://example.org/style.css +``` + +With `baseURL = https://example.org/docs/` + +```go-html-template +{{ absURL "" }} → https://example.org/docs/ +{{ absURL "articles" }} → https://example.org/docs/articles +{{ absURL "style.css" }} → https://example.org/docs/style.css +``` + +#### Input begins with a slash + +If the input begins with a slash, the resulting URL will be incorrect when the `baseURL` includes a subdirectory. With a leading slash, the function returns a URL relative to the protocol+host section of the `baseURL`. + +With `baseURL = https://example.org/` + +```go-html-template +{{ absURL "/" }} → https://example.org/ +{{ absURL "/articles" }} → https://example.org/articles +{{ absURL "/style.css" }} → https://example.org/style.css +``` + +With `baseURL = https://example.org/docs/` + +```go-html-template +{{ absURL "/" }} → https://example.org/ +{{ absURL "/articles" }} → https://example.org/articles +{{ absURL "/style.css" }} → https://example.org/style.css +``` + +{{% note %}} +The last three examples are not desirable in most situations. As a best practice, never include a leading slash when using this function. +{{% /note %}} + +[`absLangURL`]: /functions/urls/abslangurl/ diff --git a/content/en/functions/urls/Anchorize.md b/content/en/functions/urls/Anchorize.md new file mode 100644 index 000000000..15efe9a5e --- /dev/null +++ b/content/en/functions/urls/Anchorize.md @@ -0,0 +1,31 @@ +--- +title: urls.Anchorize +linkTitle: anchorize +description: Takes a string and sanitizes it the same way as the [`defaultMarkdownHandler`](/getting-started/configuration-markup#default-configuration) does for markdown headers. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [anchorize] + returnType: string + signatures: [urls.Anchorize INPUT] +relatedFunctions: + - urls.Anchorize + - urls.URLize +aliases: [/functions/anchorize] +--- + +If [Goldmark](/getting-started/configuration-markup#goldmark) is set as `defaultMarkdownHandler`, the sanitizing logic adheres to the setting [`markup.goldmark.parser.autoHeadingIDType`](/getting-started/configuration-markup#goldmark). + +Since the `defaultMarkdownHandler` and this template function use the same sanitizing logic, you can use the latter to determine the ID of a header for linking with anchor tags. + +```go-html-template +{{ anchorize "This is a header" }} → "this-is-a-header" +{{ anchorize "This is also a header" }} → "this-is-also----a-header" +{{ anchorize "main.go" }} → "maingo" +{{ anchorize "Article 123" }} → "article-123" +{{ anchorize "<- Let's try this, shall we?" }} → "--lets-try-this-shall-we" +{{ anchorize "Hello, 世界" }} → "hello-世界" +``` diff --git a/content/en/functions/urls/JoinPath.md b/content/en/functions/urls/JoinPath.md new file mode 100644 index 000000000..41adf7ee7 --- /dev/null +++ b/content/en/functions/urls/JoinPath.md @@ -0,0 +1,32 @@ +--- +title: urls.JoinPath +description: Joins the provided elements into a URL string and cleans the result of any ./ or ../ elements. If the argument list is empty, JoinPath returns an empty string. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: string + signatures: [urls.JoinPath ELEMENT...] +relatedFunctions: + - path.Join + - urls.JoinPath +aliases: [/functions/urls.joinpath] +--- + +```go-html-template +{{ urls.JoinPath }} → "" +{{ urls.JoinPath "" }} → "/" +{{ urls.JoinPath "a" }} → "a" +{{ urls.JoinPath "a" "b" }} → "a/b" +{{ urls.JoinPath "/a" "b" }} → "/a/b" +{{ urls.JoinPath "https://example.org" "b" }} → "https://example.org/b" + +{{ urls.JoinPath (slice "a" "b") }} → "a/b" +``` + +Unlike the [`path.Join`] function, `urls.JoinPath` retains consecutive leading slashes. + +[`path.Join`]: /functions/path/join diff --git a/content/en/functions/urls/Parse.md b/content/en/functions/urls/Parse.md new file mode 100644 index 000000000..17c924d51 --- /dev/null +++ b/content/en/functions/urls/Parse.md @@ -0,0 +1,37 @@ +--- +title: urls.Parse +description: Parses a URL into a URL structure. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [] + returnType: URL + signatures: [urls.Parse URL] +relatedFunctions: [] +aliases: [/functions/urls.parse] +--- + +The `urls.Parse` function parses a URL into a [URL structure](https://godoc.org/net/url#URL). The URL may be relative (a path, without a host) or absolute (starting with a [scheme]). Hugo throws an error when parsing an invalid URL. + +[scheme]: https://www.iana.org/assignments/uri-schemes/uri-schemes.xhtml#uri-schemes-1 + + +```go-html-template +{{ $url := "https://example.org:123/foo?a=6&b=7#bar" }} +{{ $u := urls.Parse $url }} + +{{ $u.IsAbs }} → true +{{ $u.Scheme }} → https +{{ $u.Host }} → example.org:123 +{{ $u.Hostname }} → example.org +{{ $u.RequestURI }} → /foo?a=6&b=7 +{{ $u.Path }} → /foo +{{ $u.Query }} → map[a:[6] b:[7]] +{{ $u.Query.a }} → [6] +{{ $u.Query.Get "a" }} → 6 +{{ $u.Query.Has "b" }} → true +{{ $u.Fragment }} → bar +``` diff --git a/content/en/functions/urls/Ref.md b/content/en/functions/urls/Ref.md new file mode 100644 index 000000000..908fd6ca8 --- /dev/null +++ b/content/en/functions/urls/Ref.md @@ -0,0 +1,49 @@ +--- +title: urls.Ref +linkTitle: ref +description: Returns the absolute permalink to a page. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [ref] + returnType: template.HTML + signatures: [urls.Ref . PAGE] +relatedFunctions: + - urls.Ref + - urls.RelRef +aliases: [/functions/ref] +--- + +This function takes two arguments: + +- The context of the page from which to resolve relative paths, typically the current page (`.`) +- The path to a page, with or without a file extension, with or without an anchor. A path without a leading `/` is first resolved relative to the given context, then to the remainder of the site. + +```go-html-template +{{ ref . "about" }} +{{ ref . "about#anchor" }} +{{ ref . "about.md" }} +{{ ref . "about.md#anchor" }} +{{ ref . "#anchor" }} +{{ ref . "/blog/my-post" }} +{{ ref . "/blog/my-post.md" }} +``` + +To return the absolute permalink to another language version of a page: + +```go-html-template +{{ ref . (dict "path" "about.md" "lang" "fr") }} +``` + +To return the absolute permalink to another Output Format of a page: + +```go-html-template +{{ ref . (dict "path" "about.md" "outputFormat" "rss") }} +``` + +Hugo emits an error or warning if the page cannot be uniquely resolved. The error behavior is configurable; see [Ref and RelRef Configuration](/content-management/cross-references/#ref-and-relref-configuration). + +This function is used by Hugo's built-in [`ref`](/content-management/shortcodes/#ref-and-relref) shortcode. For a detailed explanation of how to leverage this shortcode for content management, see [Links and Cross References](/content-management/cross-references/). diff --git a/content/en/functions/urls/RelLangURL.md b/content/en/functions/urls/RelLangURL.md new file mode 100644 index 000000000..b8850c71d --- /dev/null +++ b/content/en/functions/urls/RelLangURL.md @@ -0,0 +1,72 @@ +--- +title: urls.RelLangURL +linkTitle: relLangURL +description: Returns a relative URL with a language prefix, if any. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [relLangURL] + returnType: template.HTML + signatures: [urls.RelLangURL INPUT] +relatedFunctions: + - urls.AbsLangURL + - urls.AbsURL + - urls.RelLangURL + - urls.RelURL +aliases: [/functions/rellangurl] +--- + +Use this function with both monolingual and multilingual configurations. The URL returned by this function depends on: + +- Whether the input begins with a slash +- The `baseURL` in site configuration +- The language prefix, if any + +In examples that follow, the project is multilingual with content in both Español (`es`) and English (`en`). The default language is Español. The returned values are from the English site. + +### Input does not begin with a slash + +If the input does not begin with a slash, the resulting URL will be correct regardless of the `baseURL`. + +With `baseURL = https://example.org/` + +```go-html-template +{{ relLangURL "" }} → /en/ +{{ relLangURL "articles" }} → /en/articles +{{ relLangURL "style.css" }} → /en/style.css +``` + +With `baseURL = https://example.org/docs/` + +```go-html-template +{{ relLangURL "" }} → /docs/en/ +{{ relLangURL "articles" }} → /docs/en/articles +{{ relLangURL "style.css" }} → /docs/en/style.css +``` + +#### Input begins with a slash + +If the input begins with a slash, the resulting URL will be incorrect when the `baseURL` includes a subdirectory. With a leading slash, the function returns a URL relative to the protocol+host section of the `baseURL`. + +With `baseURL = https://example.org/` + +```go-html-template +{{ relLangURL "/" }} → /en/ +{{ relLangURL "/articles" }} → /en/articles +{{ relLangURL "/style.css" }} → /en/style.css +``` + +With `baseURL = https://example.org/docs/` + +```go-html-template +{{ relLangURL "/" }} → /en/ +{{ relLangURL "/articles" }} → /en/articles +{{ relLangURL "/style.css" }} → /en/style.css +``` + +{{% note %}} +The last three examples are not desirable in most situations. As a best practice, never include a leading slash when using this function. +{{% /note %}} diff --git a/content/en/functions/urls/RelRef.md b/content/en/functions/urls/RelRef.md new file mode 100644 index 000000000..1ff213b70 --- /dev/null +++ b/content/en/functions/urls/RelRef.md @@ -0,0 +1,56 @@ +--- +title: urls.RelRef +linkTitle: relref +description: Returns the relative permalink to a page. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [relref] + returnType: template.HTML + signatures: [urls.RelRef . PAGE] +relatedFunctions: + - urls.Ref + - urls.RelRef +aliases: [/functions/relref] +--- + +This function takes two arguments: + +- The context of the page from which to resolve relative paths, typically the current page (`.`) +- The path to a page, with or without a file extension, with or without an anchor. A path without a leading `/` is first resolved relative to the given context, then to the remainder of the site. + +```go-html-template +{{ relref . "about" }} +{{ relref . "about#anchor" }} +{{ relref . "about.md" }} +{{ relref . "about.md#anchor" }} +{{ relref . "#anchor" }} +{{ relref . "/blog/my-post" }} +{{ relref . "/blog/my-post.md" }} +``` + +The permalink returned is relative to the protocol+host portion of the baseURL specified in the site configuration. For example: + +Code|baseURL|Permalink +:--|:--|:-- +`{{ relref . "/about" }}`|`http://example.org/`|`/about/` +`{{ relref . "/about" }}`|`http://example.org/x/`|`/x/about/` + +To return the relative permalink to another language version of a page: + +```go-html-template +{{ relref . (dict "path" "about.md" "lang" "fr") }} +``` + +To return the relative permalink to another Output Format of a page: + +```go-html-template +{{ relref . (dict "path" "about.md" "outputFormat" "rss") }} +``` + +Hugo emits an error or warning if the page cannot be uniquely resolved. The error behavior is configurable; see [Ref and RelRef Configuration](/content-management/cross-references/#ref-and-relref-configuration). + +This function is used by Hugo's built-in [`relref`](/content-management/shortcodes/#ref-and-relref) shortcode. For a detailed explanation of how to leverage this shortcode for content management, see [Links and Cross References](/content-management/cross-references/). diff --git a/content/en/functions/urls/RelURL.md b/content/en/functions/urls/RelURL.md new file mode 100644 index 000000000..fa1f9af73 --- /dev/null +++ b/content/en/functions/urls/RelURL.md @@ -0,0 +1,71 @@ +--- +title: urls.RelURL +linkTitle: relURL +description: Returns a relative URL. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [relURL] + returnType: template.HTML + signatures: [urls.RelURL INPUT] +relatedFunctions: + - urls.AbsLangURL + - urls.AbsURL + - urls.RelLangURL + - urls.RelURL +aliases: [/functions/relurl] +--- + +With multilingual configurations, use the [`relLangURL`] function instead. The URL returned by this function depends on: + +- Whether the input begins with a slash +- The `baseURL` in site configuration + +### Input does not begin with a slash + +If the input does not begin with a slash, the resulting URL will be correct regardless of the `baseURL`. + +With `baseURL = https://example.org/` + +```go-html-template +{{ relURL "" }} → / +{{ relURL "articles" }} → /articles +{{ relURL "style.css" }} → /style.css +``` + +With `baseURL = https://example.org/docs/` + +```go-html-template +{{ relURL "" }} → /docs/ +{{ relURL "articles" }} → /docs/articles +{{ relURL "style.css" }} → /docs/style.css +``` + +#### Input begins with a slash + +If the input begins with a slash, the resulting URL will be incorrect when the `baseURL` includes a subdirectory. With a leading slash, the function returns a URL relative to the protocol+host section of the `baseURL`. + +With `baseURL = https://example.org/` + +```go-html-template +{{ relURL "/" }} → / +{{ relURL "/articles" }} → /articles +{{ relURL "style.css" }} → /style.css +``` + +With `baseURL = https://example.org/docs/` + +```go-html-template +{{ relURL "/" }} → / +{{ relURL "/articles" }} → /articles +{{ relURL "/style.css" }} → /style.css +``` + +{{% note %}} +The last three examples are not desirable in most situations. As a best practice, never include a leading slash when using this function. +{{% /note %}} + +[`relLangURL`]: /functions/urls/rellangurl/ diff --git a/content/en/functions/urls/URLize.md b/content/en/functions/urls/URLize.md new file mode 100644 index 000000000..3c80a92f8 --- /dev/null +++ b/content/en/functions/urls/URLize.md @@ -0,0 +1,69 @@ +--- +title: urls.URLize +linkTitle: urlize +description: Takes a string, sanitizes it for usage in URLs, and converts spaces to hyphens. +categories: [functions] +keywords: [] +menu: + docs: + parent: functions +function: + aliases: [urlize] + returnType: string + signatures: [urls.URLize INPUT] +relatedFunctions: + - urls.Anchorize + - urls.URLize +aliases: [/functions/urlize] +--- + +The following examples pull from a content file with the following front matter: + +{{< code-toggle file="content/blog/greatest-city.md" fm=true copy=false >}} +title = "The World's Greatest City" +location = "Chicago IL" +tags = ["pizza","beer","hot dogs"] +{{< /code-toggle >}} + +The following might be used as a partial within a [single page template][singletemplate]: + +{{< code file="layouts/partials/content-header.html" >}} +
+

{{ .Title }}

+ {{ with .Params.location }} + + {{ end }} + + {{ with .Params.tags }} +
    + {{ range .}} +
  • + {{ . }} +
  • + {{ end }} +
+ {{ end }} +
+{{< /code >}} + +The preceding partial would then output to the rendered page as follows: + +```html +
+

The World's Greatest City

+ + +
+``` + +[singletemplate]: /templates/single-page-templates/ diff --git a/content/en/functions/where.md b/content/en/functions/where.md deleted file mode 100644 index 9618ea4c6..000000000 --- a/content/en/functions/where.md +++ /dev/null @@ -1,180 +0,0 @@ ---- -title: where -description: Filters an array to only the elements containing a matching value for a given field. -categories: [functions] -menu: - docs: - parent: functions -keywords: [filtering] -signature: ["where COLLECTION KEY [OPERATOR] MATCH"] -relatedfuncs: [intersect,first,after,last] -toc: true ---- - -`where` filters an array to only the elements containing a matching -value for a given field. - -It works in a similar manner to the [`where` keyword in -SQL][wherekeyword]. - -```go-html-template -{{ range where .Pages "Section" "foo" }} - {{ .Content }} -{{ end }} -``` - -It can be used by dot-chaining the second argument to refer to a nested element of a value. - -{{< code-toggle file="content/example.md" fm=true copy=false >}} -title: Example -series: golang -{{< /code-toggle >}} - -```go-html-template -{{ range where .Site.Pages "Params.series" "golang" }} - {{ .Content }} -{{ end }} -``` - -It can also be used with the logical operators `!=`, `>=`, `in`, etc. Without an operator, `where` compares a given field with a matching value equivalent to `=`. - -```go-html-template -{{ range where .Pages "Section" "!=" "foo" }} - {{ .Content }} -{{ end }} -``` - -The following logical operators are available with `where`: - -`=`, `==`, `eq` -: `true` if a given field value equals a matching value - -`!=`, `<>`, `ne` -: `true` if a given field value doesn't equal a matching value - -`>=`, `ge` -: `true` if a given field value is greater than or equal to a matching value - -`>`, `gt` -: `true` if a given field value is greater than a matching value - -`<=`, `le` -: `true` if a given field value is lesser than or equal to a matching value - -`<`, `lt` -: `true` if a given field value is lesser than a matching value - -`in` -: `true` if a given field value is included in a matching value; a matching value must be an array or a slice - -`not in` -: `true` if a given field value isn't included in a matching value; a matching value must be an array or a slice - -`intersect` -: `true` if a given field value that is a slice/array of strings or integers contains elements in common with the matching value; it follows the same rules as the [`intersect` function][intersect]. - -`like` -: `true` if a given field value matches a regular expression. Use the `like` operator to compare `string` values. Returns `false` when comparing other data types to the regular expression. - -## Use `where` with boolean values -When using booleans you should not put quotation marks. -```go-html-template -{{ range where .Pages "Draft" true }} -

{{ .Title }}

-{{ end }} -``` - -## Use `where` with `intersect` - -```go-html-template -{{ range where .Site.Pages "Params.tags" "intersect" .Params.tags }} - {{ if ne .Permalink $.Permalink }} - {{ .Render "summary" }} - {{ end }} -{{ end }} -``` - -You can also put the returned value of the `where` clauses into a variable: - -{{< code file="where-intersect-variables.html" >}} -{{ $v1 := where .Site.Pages "Params.a" "v1" }} -{{ $v2 := where .Site.Pages "Params.b" "v2" }} -{{ $filtered := $v1 | intersect $v2 }} -{{ range $filtered }} -{{ end }} -{{< /code >}} - -## Use `where` with `like` - -This example matches pages where the "foo" parameter begins with "ab": - -```go-html-template -{{ range where site.RegularPages "Params.foo" "like" `^ab` }} -

{{ .LinkTitle }}

-{{ end }} -``` - -{{% readfile file="/functions/common/regular-expressions.md" %}} - -## Use `where` with `first` - -Using `first` and `where` together can be very -powerful. Below snippet gets a list of posts only from [**main -sections**](#mainsections), sorts it using the [default -ordering](/templates/lists/) for lists (i.e., `weight => date`), and -then ranges through only the first 5 posts in that list: - -{{< code file="first-and-where-together.html" >}} -{{ range first 5 (where site.RegularPages "Type" "in" site.Params.mainSections) }} - {{ .Content }} -{{ end }} -{{< /code >}} - -## Nest `where` clauses - -You can also nest `where` clauses to drill down on lists of content by more than one parameter. The following first grabs all pages in the "blog" section and then ranges through the result of the first `where` clause and finds all pages that are *not* featured: - -```go-html-template -{{ range where (where .Pages "Section" "blog" ) "Params.featured" "!=" true }} -``` - -## Unset fields - -Filtering only works for set fields. To check whether a field is set or exists, you can use the operand `nil`. - -This can be useful to filter a small amount of pages from a large pool. Instead of setting a field on all pages, you can set that field on required pages only. - -Only the following operators are available for `nil` - -* `=`, `==`, `eq`: True if the given field is not set. -* `!=`, `<>`, `ne`: True if the given field is set. - -```go-html-template -{{ range where .Pages "Params.specialpost" "!=" nil }} - {{ .Content }} -{{ end }} -``` - -## Portable `where` filters -- `site.Params.mainSections` {#mainsections} - -**This is especially important for themes.** - -To list the most relevant pages on the front page or similar, you -should use the `site.Params.mainSections` list instead of comparing -section names to hard-coded values like `"posts"` or `"post"`. - -```go-html-template -{{ $pages := where site.RegularPages "Type" "in" site.Params.mainSections }} -``` - -If the user has not set this configuration parameter in their site configuration, it will default to the *section with the most pages*. - -The user can override the default: - -{{< code-toggle file="hugo" >}} -[params] - mainSections = ["blog", "docs"] -{{< /code-toggle >}} - -[intersect]: /functions/intersect/ -[wherekeyword]: https://www.techonthenet.com/sql/where.php diff --git a/content/en/functions/with.md b/content/en/functions/with.md deleted file mode 100644 index 591aea01e..000000000 --- a/content/en/functions/with.md +++ /dev/null @@ -1,27 +0,0 @@ ---- -title: with -description: Rebinds the context (`.`) within its scope and skips the block if the variable is absent or empty. -categories: [functions] -menu: - docs: - parent: functions -keywords: [conditionals] -signature: ["with INPUT"] -relatedfuncs: [] ---- - -An alternative way of writing an `if` statement and then referencing the same value is to use `with` instead. `with` rebinds the context (`.`) within its scope and skips the block if the variable is absent, unset or empty. - -The set of *empty* values is defined by [the Go templates package](https://golang.org/pkg/text/template/). Empty values include `false`, the number zero, and the empty string. - -If you want to render a block if an index or key is present in a slice, array, channel or map, regardless of whether the value is empty, you should use [`isset`](/functions/isset) instead. - -The following example checks for a [user-defined site variable](/variables/site/) called `twitteruser`. If the key-value is not set, the following will render nothing: - -{{< code file="layouts/partials/twitter.html" >}} -{{ with .Site.Params.twitteruser }}{{ end }} -{{< /code >}} diff --git a/content/en/getting-started/configuration-markup.md b/content/en/getting-started/configuration-markup.md index dca2b3c52..02c4ea998 100644 --- a/content/en/getting-started/configuration-markup.md +++ b/content/en/getting-started/configuration-markup.md @@ -12,21 +12,47 @@ slug: configuration-markup toc: true --- -## Default configuration +## Default handler -See [Goldmark](#goldmark) for settings related to the default markdown handler in Hugo. +By default, Hugo uses [Goldmark] to render markdown to HTML. -Below are all markup related configuration in Hugo with their default settings: +{{< code-toggle file=hugo copy=false >}} +[markup] +defaultMarkdownHandler = 'goldmark' +{{< /code-toggle >}} -{{< code-toggle config="markup" />}} +Files with the `.md` or `.markdown` extension are processed as markdown, provided that you have not specified a different [content format] using the `markup` field in front matter. -**See each section below for details.** +To use a different renderer for markdown files, specify one of `asciidocext`, `org`, `pandoc`, or `rst` in your site configuration. -## Goldmark +defaultMarkdownHandler|Description +:--|:-- +`asciidocext`|[AsciiDoc] +`goldmark`|[Goldmark] +`org`|[Emacs Org Mode] +`pandoc`|[Pandoc] +`rst`|[reStructuredText] + +To use Asciidoc, Pandoc, or reStructuredText you must install the relevant renderer and update your [security policy]. + +{{% note %}} +Unless you need a unique capability provided by one of the alternate markdown handlers, we strongly recommend that you use the default setting. Goldmark is fast, well maintained, conforms to the [CommonMark] specification, and is compatible with [GitHub Flavored Markdown] (GFM). + +[commonmark]: https://spec.commonmark.org/0.30/ +[github flavored markdown]: https://github.github.com/gfm/ +{{% /note %}} -[Goldmark](https://github.com/yuin/goldmark/) is from Hugo 0.60 the default library used for Markdown. It's fast, it's [CommonMark](https://spec.commonmark.org/current/) compliant and it's very flexible. +[asciidoc]: https://asciidoc.org/ +[content format]: /content-management/formats/#list-of-content-formats +[emacs org mode]: https://orgmode.org/ +[goldmark]: https://github.com/yuin/goldmark/ +[pandoc]: https://pandoc.org/ +[restructuredtext]: https://docutils.sourceforge.io/rst.html +[security policy]: /about/security-model/#security-policy -This is the default configuration: +## Goldmark + +This is the default configuration for the Goldmark markdown renderer: {{< code-toggle config="markup.goldmark" />}} @@ -41,7 +67,21 @@ unsafe : By default, Goldmark does not render raw HTML and potentially dangerous links. If you have lots of inline HTML and/or JavaScript, you may need to turn this on. typographer -: This extension substitutes punctuations with typographic entities like [smartypants](https://daringfireball.net/projects/smartypants/). +: The typographer extension replaces certain character combinations with HTML entities as specified below: + +Markdown|Replaced by|Description +:--|:--|:-- +`...`|`…`|horizontal ellipsis +`'`|`’`|apostrophe +`--`|`–`|en dash +`---`|`—`|em dash +`«`|`«`|left angle quote +`“`|`“`|left double quote +`‘`|`‘`|left single quote +`»`|`»`|right angle quote +`”`|`”`|right double quote +`’`|`’`|right single quote + attribute : Enable custom attribute support for titles and blocks by adding attribute lists inside single curly brackets (`{.myclass class="class1 class2" }`) and placing it _after the Markdown element it decorates_, on the same line for titles and on a new line directly below for blocks. @@ -80,7 +120,71 @@ Note that attributes in [code fences](/content-management/syntax-highlighting/#h ```` autoHeadingIDType ("github") -: The strategy used for creating auto IDs (anchor names). Available types are `github`, `github-ascii` and `blackfriday`. `github` produces GitHub-compatible IDs, `github-ascii` will drop any non-Ascii characters after accent normalization, and `blackfriday` will make the IDs compatible with Blackfriday, the default Markdown engine before Hugo 0.60. Note that if Goldmark is your default Markdown engine, this is also the strategy used in the [anchorize](/functions/anchorize/) template func. +: The strategy used for creating auto IDs (anchor names). Available types are `github`, `github-ascii` and `blackfriday`. `github` produces GitHub-compatible IDs, `github-ascii` will drop any non-Ascii characters after accent normalization, and `blackfriday` will make the IDs compatible with Blackfriday, the default Markdown engine before Hugo 0.60. Note that if Goldmark is your default Markdown engine, this is also the strategy used in the [anchorize](/functions/urls/anchorize) template func. + +## Asciidoc + +This is the default configuration for the AsciiDoc markdown renderer: + +{{< code-toggle config="markup.asciidocExt" />}} + +attributes +: (`map`) Variables to be referenced in your AsciiDoc file. This is a list of variable name/value maps. See Asciidoctor’s [attributes]. + +[attributes]: https://asciidoctor.org/docs/asciidoc-syntax-quick-reference/#attributes-and-substitutions + +backend: +: (`string`) Don’t change this unless you know what you are doing. + +extensions +: (`[]string`) Possible extensions are `asciidoctor-html5s`, `asciidoctor-bibtex`, `asciidoctor-diagram`, `asciidoctor-interdoc-reftext`, `asciidoctor-katex`, `asciidoctor-latex`, `asciidoctor-mathematical`, and `asciidoctor-question`. + +failureLevel +: (`string`) The minimum logging level that triggers a non-zero exit code (failure). + +noHeaderOrFooter +: (`bool`) Output an embeddable document, which excludes the header, the footer, and everything outside the body of the document. Don’t change this unless you know what you are doing. + +preserveTOC +: (`bool`) By default, Hugo removes the table of contents generated by Asciidoctor and provides it through the built-in variable `.TableOfContents` to enable further customization and better integration with the various Hugo themes. This option can be set to true to preserve Asciidoctor’s TOC in the generated page. + +safeMode +: (`string`) Safe mode level `unsafe`, `safe`, `server`, or `secure`. Don’t change this unless you know what you are doing. + +sectionNumbers +: (`bool`) Auto-number section titles. + +trace +: (`bool`) Include backtrace information on errors. + +verbose +: (`bool`) Verbosely print processing information and configuration file checks to stderr. + +workingFolderCurrent +: (`bool`) Sets the working directory to be the same as that of the AsciiDoc file being processed, so that [include] will work with relative paths. This setting uses the asciidoctor cli parameter --base-dir and attribute outdir=. For rendering diagrams with [asciidoctor-diagram], `workingFolderCurrent` must be set to `true`. + +[asciidoctor-diagram]: https://asciidoctor.org/docs/asciidoctor-diagram/ +[include]: https://asciidoctor.org/docs/asciidoc-syntax-quick-reference/#include-files + +Notice that for security concerns only extensions that do not have path separators (either `\`, `/` or `.`) are allowed. That means that extensions can only be invoked if they are in the Ruby's `$LOAD_PATH` (ie. most likely, the extension has been installed by the user). Any extension declared relative to the website's path will not be accepted. + +Example of how to set extensions and attributes: + +```yml +[markup.asciidocExt] + extensions = ["asciidoctor-html5s", "asciidoctor-diagram"] + workingFolderCurrent = true + [markup.asciidocExt.attributes] + my-base-url = "https://example.com/" + my-attribute-name = "my value" +``` + +In a complex Asciidoctor environment it is sometimes helpful to debug the exact call to your external helper with all +parameters. Run Hugo with `-v`. You will get an output like + +```txt +INFO 2019/12/22 09:08:48 Rendering book-as-pdf.adoc with C:\Ruby26-x64\bin\asciidoctor.bat using asciidoc args [--no-header-footer -r asciidoctor-html5s -b html5s -r asciidoctor-diagram --base-dir D:\prototypes\hugo_asciidoc_ddd\docs -a outdir=D:\prototypes\hugo_asciidoc_ddd\build -] ... +``` ## Highlight @@ -110,6 +214,6 @@ endLevel ordered : If `true`, generates an ordered list instead of an unordered list. -## Markdown render hooks +## Render hooks See [Markdown Render Hooks](/templates/render-hooks/). diff --git a/content/en/getting-started/configuration.md b/content/en/getting-started/configuration.md index d210765ab..e72bb8d3b 100644 --- a/content/en/getting-started/configuration.md +++ b/content/en/getting-started/configuration.md @@ -400,7 +400,7 @@ URL to be used as a placeholder when a page reference cannot be found in `ref` o Removes [non-spacing marks](https://www.compart.com/en/unicode/category/Mn) from [composite characters](https://en.wikipedia.org/wiki/Precomposed_character) in content paths. ```text -content/post/hügó.md --> https://example.org/post/hugo/ +content/post/hügó.md → https://example.org/post/hugo/ ``` ### rssLimit @@ -449,7 +449,7 @@ Timeout for generating page contents, specified as a [duration](https://pkg.go.d ### timeZone -The time zone (or location), e.g. `Europe/Oslo`, used to parse front matter dates without such information and in the [`time` function](/functions/time/). The list of valid values may be system dependent, but should include `UTC`, `Local`, and any location in the [IANA Time Zone database](https://en.wikipedia.org/wiki/List_of_tz_database_time_zones). +The time zone (or location), e.g. `Europe/Oslo`, used to parse front matter dates without such information and in the [`time`] function. The list of valid values may be system dependent, but should include `UTC`, `Local`, and any location in the [IANA Time Zone database](https://en.wikipedia.org/wiki/List_of_tz_database_time_zones). ### title @@ -527,8 +527,6 @@ useResourceCacheWhen The `build.cachebusters` configuration option was added to support development using Tailwind 3.x's JIT compiler where a `build` configuration may look like this: - - {{< code-toggle file="hugo" >}} [build] [build.buildStats] @@ -616,7 +614,7 @@ status = 404 ## Configure title case -Set `titleCaseStyle` to specify the title style used by the [title](/functions/title/) template function and the automatic section titles in Hugo. +Set `titleCaseStyle` to specify the title style used by the [title](/functions/strings/title) template function and the automatic section titles in Hugo. Can be one of: @@ -684,10 +682,6 @@ To set configuration parameters, prefix the name with `HUGO_PARAMS_` If you are using snake_cased variable names, the above will not work. Hugo determines the delimiter to use by the first character after `HUGO`. This allows you to define environment variables on the form `HUGOxPARAMSxAPI_KEY=abcdefgh`, using any [allowed](https://stackoverflow.com/questions/2821043/allowed-characters-in-linux-environment-variable-names#:~:text=So%20names%20may%20contain%20any,not%20begin%20with%20a%20digit.) delimiter. -{{< todo >}} -Test and document setting parameters via JSON env var. -{{< /todo >}} - ## Ignore content and data files when rendering **Note:** This works, but we recommend you use the newer and more powerful [includeFiles and excludeFiles](/hugo-modules/configuration/#module-configuration-mounts) mount options. @@ -799,7 +793,7 @@ dir [`.Site.Params`]: /variables/site/ [directory structure]: /getting-started/directory-structure -[json]: https://www.ecma-international.org/publications/files/ECMA-ST/ECMA-404.pdf "Specification for JSON, JavaScript Object Notation" +[json]: https://www.ecma-international.org/publications/files/ECMA-ST/ECMA-404.pdf [lookup order]: /templates/lookup-order/ [Output Formats]: /templates/output-formats/ [templates]: /templates/ @@ -821,3 +815,6 @@ If this is not set, Hugo will use, in order of preference: 1. In a `hugo_cache_$USER` directory below the OS temp dir. If you want to know the current value of `cacheDir`, you can run `hugo config`, e.g: `hugo config | grep cachedir`. + + +[`time`]: /functions/time/astime diff --git a/content/en/getting-started/glossary.md b/content/en/getting-started/glossary.md index 834f72ec5..c15af5170 100644 --- a/content/en/getting-started/glossary.md +++ b/content/en/getting-started/glossary.md @@ -64,6 +64,10 @@ A markup language for creating content. Typically markdown, but may also be HTML A classification of content inferred from the top-level directory name or the `type` set in [front matter](#front-matter). Pages in the root of the content directory, including the home page, are of type "page". Accessed via `.Page.Type` in [templates](#template). See [details](/content-management/types/). +### content view + +A template called with the `.Page.Render` method. See [details](/templates/views/). + ### context Represented by a period "." within a [template action](#template-action), context is the current location in a data structure. For example, while iterating over a [collection](#collection) of pages, the context within each iteration is the page's data structure. The context received by each template depends on template type and/or how it was called. See [details](/templates/introduction/#the-dot). @@ -250,7 +254,7 @@ A packaged combination of [archetypes](#archetype), assets, content, data, [temp ### token -An identifier within a format string, beginning with a colon and replaced with a value when rendered. For example, use tokens in format strings for both [permalinks](/content-management/urls/#permalinks) and [dates](/functions/dateformat/#datetime-formatting-layouts). +An identifier within a format string, beginning with a colon and replaced with a value when rendered. For example, use tokens in format strings for both [permalinks](/content-management/urls/#permalinks) and [dates](/functions/time/format/#localization). ### type diff --git a/content/en/hosting-and-deployment/hosting-on-firebase.md b/content/en/hosting-and-deployment/hosting-on-firebase.md index 3b1ba9dcd..c58f4b752 100644 --- a/content/en/hosting-and-deployment/hosting-on-firebase.md +++ b/content/en/hosting-and-deployment/hosting-on-firebase.md @@ -47,26 +47,26 @@ From here: In new versions of Firebase, some other questions apply: -6. Set up automatic builds and deploys with GitHub? +6. Set up automatic builds and deploys with GitHub? Here you will be redirected to login in your GitHub account to get permissions. Confirm. -7. For which GitHub repository would you like to set up a GitHub workflow? (format: user/repository) +7. For which GitHub repository would you like to set up a GitHub workflow? (format: user/repository) Include the repository you will use in the format above (Account/Repo) Firebase script with retrieve credentials, create a service account you can later manage in your GitHub settings. -8. Set up the workflow to run a build script before every deploy? +8. Set up the workflow to run a build script before every deploy? Here is your opportunity to include some commands before you run the deploy. -9. Set up automatic deployment to your site's live channel when a PR is merged? +9. Set up automatic deployment to your site's live channel when a PR is merged? You can let in the default option (main) After that Firebase has been set in your project with CI/CD. After that run: -``` +```sh hugo && firebase deploy ``` diff --git a/content/en/hugo-modules/use-modules.md b/content/en/hugo-modules/use-modules.md index 27a1f6051..db269a5db 100644 --- a/content/en/hugo-modules/use-modules.md +++ b/content/en/hugo-modules/use-modules.md @@ -142,7 +142,7 @@ A common use case for a workspace is to simplify local development of a site wit A workspace can be configured in a `*.work` file and activated with the [module.workspace](/hugo-modules/configuration/) setting, which for this use is commonly controlled via the `HUGO_MODULE_WORKSPACE` OS environment variable. -See the [hugo.work](https://github.com/gohugoio/hugo/blob/master/hugo.work) file in the Hugo Docs repo for an example: +See the [hugo.work](https://github.com/gohugoio/hugo/blob/master/docs/hugo.work) file in the Hugo Docs repo for an example: ```text go 1.19 diff --git a/content/en/hugo-pipes/babel.md b/content/en/hugo-pipes/babel.md index 222b5116b..44b4e670e 100755 --- a/content/en/hugo-pipes/babel.md +++ b/content/en/hugo-pipes/babel.md @@ -8,7 +8,7 @@ menu: parent: hugo-pipes weight: 70 weight: 70 -signature: ["resources.Babel RESOURCE [OPTIONS]", "babel RESOURCE [OPTIONS]"] +signatures: ["resources.Babel RESOURCE [OPTIONS]", "babel RESOURCE [OPTIONS]"] --- ## Usage diff --git a/content/en/hugo-pipes/bundling.md b/content/en/hugo-pipes/bundling.md index 8b9899432..f3ff42f9c 100755 --- a/content/en/hugo-pipes/bundling.md +++ b/content/en/hugo-pipes/bundling.md @@ -9,7 +9,7 @@ menu: parent: hugo-pipes weight: 90 weight: 90 -signature: ["resources.Concat TARGET_PATH SLICE_RESOURCES"] +signatures: ["resources.Concat TARGET_PATH SLICE_RESOURCES"] --- ## Usage diff --git a/content/en/hugo-pipes/fingerprint.md b/content/en/hugo-pipes/fingerprint.md index bdabbe029..c492d4c70 100755 --- a/content/en/hugo-pipes/fingerprint.md +++ b/content/en/hugo-pipes/fingerprint.md @@ -9,7 +9,7 @@ menu: parent: hugo-pipes weight: 100 weight: 100 -signature: ["resources.Fingerprint RESOURCE [ALGORITHM]", "fingerprint RESOURCE [ALGORITHM]"] +signatures: ["resources.Fingerprint RESOURCE [ALGORITHM]", "fingerprint RESOURCE [ALGORITHM]"] --- ## Usage diff --git a/content/en/hugo-pipes/js.md b/content/en/hugo-pipes/js.md index 86c1564cf..ecf6dc33f 100644 --- a/content/en/hugo-pipes/js.md +++ b/content/en/hugo-pipes/js.md @@ -9,7 +9,7 @@ menu: parent: hugo-pipes weight: 60 weight: 60 -signature: ["js.Build RESOURCE [OPTIONS]"] +signatures: ["js.Build RESOURCE [OPTIONS]"] --- ## Usage diff --git a/content/en/hugo-pipes/minification.md b/content/en/hugo-pipes/minification.md index a32ef6e6f..74ddfaa89 100755 --- a/content/en/hugo-pipes/minification.md +++ b/content/en/hugo-pipes/minification.md @@ -9,7 +9,7 @@ menu: parent: hugo-pipes weight: 80 weight: 80 -signature: ["resources.Minify RESOURCE", "minify RESOURCE"] +signatures: ["resources.Minify RESOURCE", "minify RESOURCE"] --- ## Usage diff --git a/content/en/hugo-pipes/postcss.md b/content/en/hugo-pipes/postcss.md index 4e969caf2..2a08c7ad4 100755 --- a/content/en/hugo-pipes/postcss.md +++ b/content/en/hugo-pipes/postcss.md @@ -9,7 +9,7 @@ menu: weight: 40 toc: true weight: 40 -signature: ["resources.PostCSS RESOURCE [OPTIONS]", "postCSS RESOURCE [OPTIONS]"] +signatures: ["resources.PostCSS RESOURCE [OPTIONS]", "postCSS RESOURCE [OPTIONS]"] --- ## Setup diff --git a/content/en/hugo-pipes/postprocess.md b/content/en/hugo-pipes/postprocess.md index 3b7d5c610..4b3cb8ad4 100755 --- a/content/en/hugo-pipes/postprocess.md +++ b/content/en/hugo-pipes/postprocess.md @@ -8,7 +8,7 @@ menu: parent: hugo-pipes weight: 50 weight: 50 -signature: ["resources.PostProcess RESOURCE"] +signatures: ["resources.PostProcess RESOURCE"] --- ## Usage diff --git a/content/en/hugo-pipes/resource-from-string.md b/content/en/hugo-pipes/resource-from-string.md index f3f0cda4f..fa472715c 100755 --- a/content/en/hugo-pipes/resource-from-string.md +++ b/content/en/hugo-pipes/resource-from-string.md @@ -9,7 +9,7 @@ menu: parent: hugo-pipes weight: 110 weight: 110 -signature: ["resources.FromString TARGET_PATH CONTENT"] +signatures: ["resources.FromString TARGET_PATH CONTENT"] --- ## Usage diff --git a/content/en/hugo-pipes/resource-from-template.md b/content/en/hugo-pipes/resource-from-template.md index 4f34817c0..c1c4cb316 100755 --- a/content/en/hugo-pipes/resource-from-template.md +++ b/content/en/hugo-pipes/resource-from-template.md @@ -9,7 +9,7 @@ menu: parent: hugo-pipes weight: 120 weight: 120 -signature: ["resources.ExecuteAsTemplate TARGET_PATH CONTEXT RESOURCE"] +signatures: ["resources.ExecuteAsTemplate TARGET_PATH CONTEXT RESOURCE"] --- ## Usage diff --git a/content/en/hugo-pipes/transpile-sass-to-css.md b/content/en/hugo-pipes/transpile-sass-to-css.md index bf3d136f1..b09cc165b 100644 --- a/content/en/hugo-pipes/transpile-sass-to-css.md +++ b/content/en/hugo-pipes/transpile-sass-to-css.md @@ -9,7 +9,7 @@ menu: parent: hugo-pipes weight: 30 weight: 30 -signature: ["resources.ToCSS RESOURCE [OPTIONS]", "toCSS RESOURCE [OPTIONS]"] +signatures: ["resources.ToCSS RESOURCE [OPTIONS]", "toCSS RESOURCE [OPTIONS]"] toc: true aliases: [/hugo-pipes/transform-to-css/] --- diff --git a/content/en/installation/_common/01-editions.md b/content/en/installation/_common/01-editions.md new file mode 100644 index 000000000..cbc338665 --- /dev/null +++ b/content/en/installation/_common/01-editions.md @@ -0,0 +1,12 @@ +## Editions + +Hugo is available in two editions: standard and extended. With the extended edition you can: + +- Encode to the WebP format when [processing images]. You can decode WebP images with either edition. +- [Transpile Sass to CSS] using the embedded LibSass transpiler. The extended edition is not required to use the [Dart Sass] transpiler. + +We recommend that you install the extended edition. + +[dart sass]: /hugo-pipes/transpile-sass-to-css/#dart-sass +[processing images]: /content-management/image-processing/ +[transpile sass to css]: /hugo-pipes/transpile-sass-to-css/ diff --git a/content/en/installation/_common/02-prerequisites.md b/content/en/installation/_common/02-prerequisites.md new file mode 100644 index 000000000..423950113 --- /dev/null +++ b/content/en/installation/_common/02-prerequisites.md @@ -0,0 +1,36 @@ +## Prerequisites + +Although not required in all cases, [Git], [Go], and [Dart Sass] are commonly used when working with Hugo. + +Git is required to: + +- Build Hugo from source +- Use the [Hugo Modules] feature +- Install a theme as a Git submodule +- Access [commit information] from a local Git repository +- Host your site with services such as [CloudCannon], [Cloudflare Pages], [GitHub Pages], [GitLab Pages], and [Netlify] + +Go is required to: + +- Build Hugo from source +- Use the Hugo Modules feature + +Dart Sass is required to transpile Sass to CSS when using the latest features of the Sass language. + +Please refer to the relevant documentation for installation instructions: + +- [Git][git install] +- [Go][go install] +- [Dart Sass][dart sass install] + +[cloudcannon]: https://cloudcannon.com/ +[cloudflare pages]: https://pages.cloudflare.com/ +[dart sass install]: /hugo-pipes/transpile-sass-to-css/#dart-sass +[dart sass]: https://sass-lang.com/dart-sass +[git install]: https://git-scm.com/book/en/v2/Getting-Started-Installing-Git +[git]: https://git-scm.com/ +[github pages]: https://pages.github.com/ +[gitlab pages]: https://docs.gitlab.com/ee/user/project/pages/ +[go install]: https://go.dev/doc/install +[go]: https://go.dev/ +[netlify]: https://www.netlify.com/ diff --git a/content/en/installation/_common/03-prebuilt-binaries.md b/content/en/installation/_common/03-prebuilt-binaries.md new file mode 100644 index 000000000..884869e1e --- /dev/null +++ b/content/en/installation/_common/03-prebuilt-binaries.md @@ -0,0 +1,21 @@ +## Prebuilt binaries + +Prebuilt binaries are available for a variety of operating systems and architectures. Visit the [latest release] page, and scroll down to the Assets section. + + +1. Download the archive for the desired [edition], operating system, and architecture +1. Extract the archive +1. Move the executable to the desired directory +1. Add this directory to the PATH environment variable +1. Verify that you have _execute_ permission on the file + +Please consult your operating system documentation if you need help setting file permissions or modifying your PATH environment variable. + +If you do not see a prebuilt binary for the desired edition, operating system, and architecture, install Hugo using one of the methods described below. + +[commit information]: /variables/git +[edition]: #editions +[Git]: https://git-scm.com/ +[Go]: https://go.dev/ +[Hugo Modules]: /hugo-modules/ +[latest release]: https://github.com/gohugoio/hugo/releases/latest diff --git a/content/en/installation/_common/04-build-from-source.md b/content/en/installation/_common/04-build-from-source.md new file mode 100644 index 000000000..7537882fd --- /dev/null +++ b/content/en/installation/_common/04-build-from-source.md @@ -0,0 +1,23 @@ +## Build from source + +To build the extended edition of Hugo from source you must: + +1. Install [Git] +1. Install [Go] version 1.19 or later +1. Install a C compiler, either [GCC] or [Clang] +1. Update your `PATH` environment variable as described in the [Go documentation] + +> The install directory is controlled by the `GOPATH` and `GOBIN` environment variables. If `GOBIN` is set, binaries are installed to that directory. If `GOPATH` is set, binaries are installed to the bin subdirectory of the first directory in the `GOPATH` list. Otherwise, binaries are installed to the bin subdirectory of the default `GOPATH` (`$HOME/go` or `%USERPROFILE%\go`). + +Then build and test: + +```sh +CGO_ENABLED=1 go install -tags extended github.com/gohugoio/hugo@latest +hugo version +``` + +[Clang]: https://clang.llvm.org/ +[GCC]: https://gcc.gnu.org/ +[Git]: https://git-scm.com/book/en/v2/Getting-Started-Installing-Git +[Go documentation]: https://go.dev/doc/code#Command +[Go]: https://go.dev/doc/install diff --git a/content/en/installation/_common/homebrew.md b/content/en/installation/_common/homebrew.md new file mode 100644 index 000000000..7178a9f4f --- /dev/null +++ b/content/en/installation/_common/homebrew.md @@ -0,0 +1,9 @@ +### Homebrew + +[Homebrew] is a free and open source package manager for macOS and Linux. This will install the extended edition of Hugo: + +```sh +brew install hugo +``` + +[Homebrew]: https://brew.sh/ diff --git a/content/en/installation/_common/index.md b/content/en/installation/_common/index.md new file mode 100644 index 000000000..cbb7365a6 --- /dev/null +++ b/content/en/installation/_common/index.md @@ -0,0 +1,3 @@ ++++ +headless = true ++++ diff --git a/content/en/installation/bsd.md b/content/en/installation/bsd.md index 5fbc4bfad..999e52ad6 100644 --- a/content/en/installation/bsd.md +++ b/content/en/installation/bsd.md @@ -9,11 +9,11 @@ menu: toc: true weight: 50 --- -{{% readfile file="/installation/common/01-editions.md" %}} +{{% readfile file="/installation/_common/01-editions.md" %}} -{{% readfile file="/installation/common/02-prerequisites.md" %}} +{{% readfile file="/installation/_common/02-prerequisites.md" %}} -{{% readfile file="/installation/common/03-prebuilt-binaries.md" %}} +{{% readfile file="/installation/_common/03-prebuilt-binaries.md" %}} ## Repository packages @@ -61,7 +61,7 @@ doas pkg_add hugo [OpenBSD]: https://www.openbsd.org/ -{{% readfile file="/installation/common/05-build-from-source.md" %}} +{{% readfile file="/installation/_common/04-build-from-source.md" %}} ## Comparison diff --git a/content/en/installation/common/01-editions.md b/content/en/installation/common/01-editions.md deleted file mode 100644 index cbc338665..000000000 --- a/content/en/installation/common/01-editions.md +++ /dev/null @@ -1,12 +0,0 @@ -## Editions - -Hugo is available in two editions: standard and extended. With the extended edition you can: - -- Encode to the WebP format when [processing images]. You can decode WebP images with either edition. -- [Transpile Sass to CSS] using the embedded LibSass transpiler. The extended edition is not required to use the [Dart Sass] transpiler. - -We recommend that you install the extended edition. - -[dart sass]: /hugo-pipes/transpile-sass-to-css/#dart-sass -[processing images]: /content-management/image-processing/ -[transpile sass to css]: /hugo-pipes/transpile-sass-to-css/ diff --git a/content/en/installation/common/02-prerequisites.md b/content/en/installation/common/02-prerequisites.md deleted file mode 100644 index 423950113..000000000 --- a/content/en/installation/common/02-prerequisites.md +++ /dev/null @@ -1,36 +0,0 @@ -## Prerequisites - -Although not required in all cases, [Git], [Go], and [Dart Sass] are commonly used when working with Hugo. - -Git is required to: - -- Build Hugo from source -- Use the [Hugo Modules] feature -- Install a theme as a Git submodule -- Access [commit information] from a local Git repository -- Host your site with services such as [CloudCannon], [Cloudflare Pages], [GitHub Pages], [GitLab Pages], and [Netlify] - -Go is required to: - -- Build Hugo from source -- Use the Hugo Modules feature - -Dart Sass is required to transpile Sass to CSS when using the latest features of the Sass language. - -Please refer to the relevant documentation for installation instructions: - -- [Git][git install] -- [Go][go install] -- [Dart Sass][dart sass install] - -[cloudcannon]: https://cloudcannon.com/ -[cloudflare pages]: https://pages.cloudflare.com/ -[dart sass install]: /hugo-pipes/transpile-sass-to-css/#dart-sass -[dart sass]: https://sass-lang.com/dart-sass -[git install]: https://git-scm.com/book/en/v2/Getting-Started-Installing-Git -[git]: https://git-scm.com/ -[github pages]: https://pages.github.com/ -[gitlab pages]: https://docs.gitlab.com/ee/user/project/pages/ -[go install]: https://go.dev/doc/install -[go]: https://go.dev/ -[netlify]: https://www.netlify.com/ diff --git a/content/en/installation/common/03-prebuilt-binaries.md b/content/en/installation/common/03-prebuilt-binaries.md deleted file mode 100644 index 884869e1e..000000000 --- a/content/en/installation/common/03-prebuilt-binaries.md +++ /dev/null @@ -1,21 +0,0 @@ -## Prebuilt binaries - -Prebuilt binaries are available for a variety of operating systems and architectures. Visit the [latest release] page, and scroll down to the Assets section. - - -1. Download the archive for the desired [edition], operating system, and architecture -1. Extract the archive -1. Move the executable to the desired directory -1. Add this directory to the PATH environment variable -1. Verify that you have _execute_ permission on the file - -Please consult your operating system documentation if you need help setting file permissions or modifying your PATH environment variable. - -If you do not see a prebuilt binary for the desired edition, operating system, and architecture, install Hugo using one of the methods described below. - -[commit information]: /variables/git -[edition]: #editions -[Git]: https://git-scm.com/ -[Go]: https://go.dev/ -[Hugo Modules]: /hugo-modules/ -[latest release]: https://github.com/gohugoio/hugo/releases/latest diff --git a/content/en/installation/common/04-docker.md b/content/en/installation/common/04-docker.md deleted file mode 100644 index 24f5cd942..000000000 --- a/content/en/installation/common/04-docker.md +++ /dev/null @@ -1,10 +0,0 @@ -## Docker - -[Erlend Klakegg Bergheim] graciously maintains [Docker images] based on images for Alpine Linux, Busybox, Debian, and Ubuntu. - -```sh -docker pull klakegg/hugo -``` - -[Docker images]: https://hub.docker.com/r/klakegg/hugo -[Erlend Klakegg Bergheim]: https://github.com/klakegg diff --git a/content/en/installation/common/05-build-from-source.md b/content/en/installation/common/05-build-from-source.md deleted file mode 100644 index 7537882fd..000000000 --- a/content/en/installation/common/05-build-from-source.md +++ /dev/null @@ -1,23 +0,0 @@ -## Build from source - -To build the extended edition of Hugo from source you must: - -1. Install [Git] -1. Install [Go] version 1.19 or later -1. Install a C compiler, either [GCC] or [Clang] -1. Update your `PATH` environment variable as described in the [Go documentation] - -> The install directory is controlled by the `GOPATH` and `GOBIN` environment variables. If `GOBIN` is set, binaries are installed to that directory. If `GOPATH` is set, binaries are installed to the bin subdirectory of the first directory in the `GOPATH` list. Otherwise, binaries are installed to the bin subdirectory of the default `GOPATH` (`$HOME/go` or `%USERPROFILE%\go`). - -Then build and test: - -```sh -CGO_ENABLED=1 go install -tags extended github.com/gohugoio/hugo@latest -hugo version -``` - -[Clang]: https://clang.llvm.org/ -[GCC]: https://gcc.gnu.org/ -[Git]: https://git-scm.com/book/en/v2/Getting-Started-Installing-Git -[Go documentation]: https://go.dev/doc/code#Command -[Go]: https://go.dev/doc/install diff --git a/content/en/installation/common/homebrew.md b/content/en/installation/common/homebrew.md deleted file mode 100644 index 7178a9f4f..000000000 --- a/content/en/installation/common/homebrew.md +++ /dev/null @@ -1,9 +0,0 @@ -### Homebrew - -[Homebrew] is a free and open source package manager for macOS and Linux. This will install the extended edition of Hugo: - -```sh -brew install hugo -``` - -[Homebrew]: https://brew.sh/ diff --git a/content/en/installation/common/index.md b/content/en/installation/common/index.md deleted file mode 100644 index cbb7365a6..000000000 --- a/content/en/installation/common/index.md +++ /dev/null @@ -1,3 +0,0 @@ -+++ -headless = true -+++ diff --git a/content/en/installation/linux.md b/content/en/installation/linux.md index 4056b987a..2dbbd3720 100644 --- a/content/en/installation/linux.md +++ b/content/en/installation/linux.md @@ -9,11 +9,11 @@ menu: toc: true weight: 30 --- -{{% readfile file="/installation/common/01-editions.md" %}} +{{% readfile file="/installation/_common/01-editions.md" %}} -{{% readfile file="/installation/common/02-prerequisites.md" %}} +{{% readfile file="/installation/_common/02-prerequisites.md" %}} -{{% readfile file="/installation/common/03-prebuilt-binaries.md" %}} +{{% readfile file="/installation/_common/03-prebuilt-binaries.md" %}} ## Package managers @@ -47,7 +47,7 @@ sudo snap disconnect hugo:ssh-keys [strictly confined]: https://snapcraft.io/docs/snap-confinement [Snap]: https://snapcraft.io/ -{{% readfile file="/installation/common/homebrew.md" %}} +{{% readfile file="/installation/_common/homebrew.md" %}} ## Repository packages @@ -124,20 +124,17 @@ sudo eopkg install hugo [Solus]: https://getsol.us/ -{{% readfile file="/installation/common/04-docker.md" %}} - -{{% readfile file="/installation/common/05-build-from-source.md" %}} +{{% readfile file="/installation/_common/04-build-from-source.md" %}} ## Comparison -||Prebuilt binaries|Package managers|Repository packages|Docker|Build from source -:--|:--:|:--:|:--:|:--:|:--: -Easy to install?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark: -Easy to upgrade?|:heavy_check_mark:|:heavy_check_mark:|varies|:heavy_check_mark:|:heavy_check_mark: -Easy to downgrade?|:heavy_check_mark:|:heavy_check_mark: [^1]|varies|:heavy_check_mark:|:heavy_check_mark: -Automatic updates?|:x:|varies [^2]|:x:|:x: [^3]|:x: -Latest version available?|:heavy_check_mark:|:heavy_check_mark:|varies|:heavy_check_mark:|:heavy_check_mark: +||Prebuilt binaries|Package managers|Repository packages|Build from source +:--|:--:|:--:|:--:|:--: +Easy to install?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark: +Easy to upgrade?|:heavy_check_mark:|:heavy_check_mark:|varies|:heavy_check_mark: +Easy to downgrade?|:heavy_check_mark:|:heavy_check_mark: [^1]|varies|:heavy_check_mark: +Automatic updates?|:x:|varies [^2]|:x:|:x: +Latest version available?|:heavy_check_mark:|:heavy_check_mark:|varies|:heavy_check_mark: [^1]: Easy if a previous version is still installed. [^2]: Snap packages are automatically updated. Homebrew requires advanced configuration. -[^3]: Possible but requires advanced configuration. diff --git a/content/en/installation/macos.md b/content/en/installation/macos.md index 9d10642de..ccae90b36 100644 --- a/content/en/installation/macos.md +++ b/content/en/installation/macos.md @@ -9,15 +9,15 @@ menu: toc: true weight: 20 --- -{{% readfile file="/installation/common/01-editions.md" %}} +{{% readfile file="/installation/_common/01-editions.md" %}} -{{% readfile file="/installation/common/02-prerequisites.md" %}} +{{% readfile file="/installation/_common/02-prerequisites.md" %}} -{{% readfile file="/installation/common/03-prebuilt-binaries.md" %}} +{{% readfile file="/installation/_common/03-prebuilt-binaries.md" %}} ## Package managers -{{% readfile file="/installation/common/homebrew.md" %}} +{{% readfile file="/installation/_common/homebrew.md" %}} ### MacPorts @@ -29,19 +29,17 @@ sudo port install hugo [MacPorts]: https://www.macports.org/ -{{% readfile file="/installation/common/04-docker.md" %}} - -{{% readfile file="/installation/common/05-build-from-source.md" %}} +{{% readfile file="/installation/_common/04-build-from-source.md" %}} ## Comparison -||Prebuilt binaries|Package managers|Docker|Build from source -:--|:--:|:--:|:--:|:--:|:--: -Easy to install?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:| -Easy to upgrade?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark: -Easy to downgrade?|:heavy_check_mark:|:heavy_check_mark: [^1]|:heavy_check_mark:|:heavy_check_mark: -Automatic updates?|:x:|:x: [^2]|:x: [^2]|:x: -Latest version available?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark: +||Prebuilt binaries|Package managers|Build from source +:--|:--:|:--:|:--: +Easy to install?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:| +Easy to upgrade?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark: +Easy to downgrade?|:heavy_check_mark:|:heavy_check_mark: [^1]|:heavy_check_mark: +Automatic updates?|:x:|:x: [^2]|:x: +Latest version available?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark: [^1]: Easy if a previous version is still installed. [^2]: Possible but requires advanced configuration. diff --git a/content/en/installation/windows.md b/content/en/installation/windows.md index 92979d9f2..48c5f7006 100644 --- a/content/en/installation/windows.md +++ b/content/en/installation/windows.md @@ -9,11 +9,11 @@ menu: toc: true weight: 40 --- -{{% readfile file="/installation/common/01-editions.md" %}} +{{% readfile file="/installation/_common/01-editions.md" %}} -{{% readfile file="/installation/common/02-prerequisites.md" %}} +{{% readfile file="/installation/_common/02-prerequisites.md" %}} -{{% readfile file="/installation/common/03-prebuilt-binaries.md" %}} +{{% readfile file="/installation/_common/03-prebuilt-binaries.md" %}} ## Package managers @@ -47,9 +47,7 @@ winget install Hugo.Hugo.Extended [Winget]: https://learn.microsoft.com/en-us/windows/package-manager/ -{{% readfile file="/installation/common/04-docker.md" %}} - -{{% readfile file="/installation/common/05-build-from-source.md" %}} +{{% readfile file="/installation/_common/04-build-from-source.md" %}} {{% note %}} See these [detailed instructions](https://discourse.gohugo.io/t/41370) to install GCC on Windows. @@ -57,13 +55,13 @@ See these [detailed instructions](https://discourse.gohugo.io/t/41370) to instal ## Comparison -||Prebuilt binaries|Package managers|Docker|Build from source -:--|:--:|:--:|:--:|:--:|:--: -Easy to install?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:| -Easy to upgrade?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark: -Easy to downgrade?|:heavy_check_mark:|:heavy_check_mark: [^2]|:heavy_check_mark:|:heavy_check_mark: -Automatic updates?|:x:|:x: [^1]|:x: [^1]|:x: -Latest version available?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark: +||Prebuilt binaries|Package managers|Build from source +:--|:--:|:--:|:--: +Easy to install?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark:| +Easy to upgrade?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark: +Easy to downgrade?|:heavy_check_mark:|:heavy_check_mark: [^2]|:heavy_check_mark: +Automatic updates?|:x:|:x: [^1]|:x: +Latest version available?|:heavy_check_mark:|:heavy_check_mark:|:heavy_check_mark: [^1]: Possible but requires advanced configuration. [^2]: Easy if a previous version is still installed. diff --git a/content/en/readfiles/README.md b/content/en/readfiles/README.md deleted file mode 100644 index 4b10f0e47..000000000 --- a/content/en/readfiles/README.md +++ /dev/null @@ -1,16 +0,0 @@ -# readdirs Directory for Reusable Content - -Files in this directory are: - -1. Used in *more than one place* within the Hugo docs -2. Used in Examples of readdir (i.e. in local file templates) - -These files are called using the [`readfile` shortcode (source)](../layouts/readfile.html). - -You can call this shortcode in the docs as follows: - - -{{% readfile file="/path/to/file.txt" markdown="true" %}} - - -`markdown="true"` is optional (default = `"false"`) and parses the string through the Blackfriday renderer. diff --git a/content/en/readfiles/dateformatting.md b/content/en/readfiles/dateformatting.md deleted file mode 100644 index e6c395151..000000000 --- a/content/en/readfiles/dateformatting.md +++ /dev/null @@ -1,87 +0,0 @@ -Go templates [format your dates][time] according to a single reference time: - -```txt -Mon Jan 2 15:04:05 MST 2006 -``` - -You can think of `MST` as `07`, thus making the reference format string a sequence of numbers. The following is [taken directly from the Go docs][gdex]: - -```txt -Jan 2 15:04:05 2006 MST - 1 2 3 4 5 6 -7 -``` - -### Hugo date templating reference - -Each of the following examples show the reference formatting string followed by the string Hugo will output in your HTML. - -Note that the examples were rendered and tested in [CST] and pull from a single example date you might have in your content's front matter: - -```yml -date: 2017-03-03T14:15:59-06:00 -``` - -`.Date` (i.e. called via [page variable][pagevars]) -: **Returns**: `2017-03-03 14:15:59 -0600 CST` - -`"Monday, January 2, 2006"` -: **Returns**: `Friday, March 3, 2017` - -`"Mon Jan 2 2006"` -: **Returns**: `Fri Mar 3 2017` - -`"January 2nd"` -: **Returns**: `March 3rd` - -`"January 2006"` -: **Returns**: `March 2017` - -`"2006-01-02"` -: **Returns**: `2017-03-03` - -`"Monday"` -: **Returns**: `Friday` - -`"02 Jan 06 15:04 MST"` (RFC822) -: **Returns**: `03 Mar 17 14:15 CST` - -`"02 Jan 06 15:04 -0700"` (RFC822Z) -: **Returns**: `03 Mar 17 14:15 -0600` - -`"Mon, 02 Jan 2006 15:04:05 MST"` (RFC1123) -: **Returns**: `Fri, 03 Mar 2017 14:15:59 CST` - -`"Mon, 02 Jan 2006 15:04:05 -0700"` (RFC339) -: **Returns**: `Fri, 03 Mar 2017 14:15:59 -0600` - -### Cardinal numbers and ordinal abbreviations - -Spelled-out cardinal numbers (e.g. "one", "two", and "three") and ordinal abbreviations (e.g. "1st", "2nd", and "3rd") are not currently supported. - -To continue with the example above: - -```go-html-template -{{ .Date.Format "Jan 2nd 2006" }} -``` - -Hugo assumes you want to append `nd` as a string to the day of the month and outputs the following: - -```txt -Mar 2nd 2017 -``` - -### Use `.Local` and `.UTC` - -In conjunction with the [`dateFormat` function][dateFormat], you can also convert your dates to `UTC` or to local timezones: - -`{{ dateFormat "02 Jan 06 15:04 MST" .Date.UTC }}` -: **Returns**: `03 Mar 17 20:15 UTC` - -`{{ dateFormat "02 Jan 06 15:04 MST" .Date.Local }}` -: **Returns**: `03 Mar 17 14:15 CST` - -[CST]: https://en.wikipedia.org/wiki/Central_Time_Zone -[dateFormat]: /functions/dateformat/ -[gdex]: https://golang.org/pkg/time/#example_Time_Format -[pagevars]: /variables/page/ -[time]: https://golang.org/pkg/time/ diff --git a/content/en/readfiles/index.md b/content/en/readfiles/index.md deleted file mode 100644 index 3d65eaa0f..000000000 --- a/content/en/readfiles/index.md +++ /dev/null @@ -1,3 +0,0 @@ ---- -headless: true ---- \ No newline at end of file diff --git a/content/en/readfiles/sectionvars.md b/content/en/readfiles/sectionvars.md deleted file mode 100644 index 45aaff1f3..000000000 --- a/content/en/readfiles/sectionvars.md +++ /dev/null @@ -1,23 +0,0 @@ -.CurrentSection -: The page's current section. The value can be the page itself if it is a section or the homepage. - -.FirstSection -: The page's first section below root, e.g. `/docs`, `/blog` etc. - -.InSection $anotherPage -: Whether the given page is in the current section. - -.IsAncestor $anotherPage -: Whether the current page is an ancestor of the given page. - -.IsDescendant $anotherPage -: Whether the current page is a descendant of the given page. - -.Parent -: A section's parent section or a page's section. - -.Section -: The [section](/content-management/sections/) this content belongs to. **Note:** For nested sections, this is the first path element in the directory, for example, `/blog/funny/mypost/ => blog`. - -.Sections -: The [sections](/content-management/sections/) below this content. diff --git a/content/en/readfiles/testing.txt b/content/en/readfiles/testing.txt deleted file mode 100644 index 6428710e3..000000000 --- a/content/en/readfiles/testing.txt +++ /dev/null @@ -1,3 +0,0 @@ -##### Hello World! - -Testing one, **two**, *three*. Don't delete this sample file used in the [templates](/templates/) section of the Hugo docs. \ No newline at end of file diff --git a/content/en/showcase/overmindstudios/bio.md b/content/en/showcase/overmindstudios/bio.md new file mode 100644 index 000000000..1bd870984 --- /dev/null +++ b/content/en/showcase/overmindstudios/bio.md @@ -0,0 +1,7 @@ + +**Overmind Studios** is a visual effects studio headquartered in Southern Germany. + +The site is built by: + +* [Tobias Kummer](https://www.overmind-studios.de/about/) + diff --git a/content/en/showcase/overmindstudios/featured.png b/content/en/showcase/overmindstudios/featured.png new file mode 100644 index 000000000..c3eaaaf4c Binary files /dev/null and b/content/en/showcase/overmindstudios/featured.png differ diff --git a/content/en/showcase/overmindstudios/index.md b/content/en/showcase/overmindstudios/index.md new file mode 100644 index 000000000..3208b2b72 --- /dev/null +++ b/content/en/showcase/overmindstudios/index.md @@ -0,0 +1,13 @@ +--- +title: Overmind Studios +description: "A fresh start to make things easier in the future." +siteURL: https://www.overmind-studios.de/ +byline: "[tobkum](https://github.com/tobkum), Co-Founder Overmind Studios" +--- +After many years of running our site on WordPress, we decided to switch to Hugo. + +WordPress is a great CMS for many people, but it has some downsides, especially for those who need a fast, secure, and customizable site. Plugins can become outdated, customization can be difficult, and bloat can slow down page loading times. + +Hugo is a static site generator that addresses many of these problems. It is fast to build and iterate, does not require PHP, is highly customizable, and is easy to learn and use. It is also secure, as it does not have a backend or MySQL database that can be hacked. + +We are very happy with our switch to Hugo. It is easy to update our site with new projects, and our Lighthouse score and loading times are both excellent. We now have more time to be creative instead of troubleshooting WordPress quirks and updates. diff --git a/content/en/templates/data-templates.md b/content/en/templates/data-templates.md index 0aadbb9ae..cf835af44 100644 --- a/content/en/templates/data-templates.md +++ b/content/en/templates/data-templates.md @@ -20,7 +20,7 @@ Hugo supports loading data from YAML, JSON, XML, and TOML files located in the ` ## The data folder -The `data` folder should store additional data for Hugo to use when generating your site. +The `data` folder should store additional data for Hugo to use when generating your site. Data files are not for generating standalone pages. They should supplement content files by: @@ -37,7 +37,7 @@ To access the data using the `site.Data.filename` notation, the file name must b - `x123.json` - Valid - `_123.json` - Valid -To access the data using the [`index`](/functions/index-function/) function, the file name is irrelevant. For example: +To access the data using the [`index`](/functions/collections/indexfunction) function, the file name is irrelevant. For example: Data file|Template code :--|:-- @@ -130,8 +130,7 @@ You can use the following code to render the `Short Description` in your layout:
Short Description of {{ .Site.Data.User0123.Name }}:

{{ index .Site.Data.User0123 "Short Description" | markdownify }}

``` -Note the use of the [`markdownify` template function][markdownify]. This will send the description through the Markdown rendering engine. - +Note the use of the [`markdownify`] function. This will send the description through the Markdown rendering engine. ## Get remote data @@ -255,10 +254,10 @@ If you change any local file and the LiveReload is triggered, Hugo will read the [config]: /getting-started/configuration/ [csv]: https://tools.ietf.org/html/rfc4180 [customize]: /hugo-modules/theme-components/ -[json]: https://www.ecma-international.org/publications/files/ECMA-ST/ECMA-404.pdf "Specification for JSON, JavaScript Object Notation" +[json]: https://www.ecma-international.org/publications/files/ECMA-ST/ECMA-404.pdf [LiveReload]: /getting-started/usage/#livereload [lookup]: /templates/lookup-order/ -[markdownify]: /functions/markdownify/ +[`markdownify`]: /functions/transform/markdownify [OAuth]: https://en.wikipedia.org/wiki/OAuth [partials]: /templates/partials/ [toml]: https://toml.io/en/latest diff --git a/content/en/templates/files.md b/content/en/templates/files.md index 7b058d531..2e82688c0 100644 --- a/content/en/templates/files.md +++ b/content/en/templates/files.md @@ -14,11 +14,11 @@ toc: true ## Traverse local files -With Hugo's [`readDir`][readDir] and [`readFile`][readFile] template functions, you can traverse your website's files on your server. +With Hugo's [`readDir`] and [`readFile`] template functions, you can traverse your website's files on your server. ## Use `readDir` -The [`readDir` function][readDir] returns an array of [`os.FileInfo`][osfileinfo]. It takes the file's `path` as a single string argument. This path can be to any directory of your website (i.e., as found on your server's file system). +The [`readDir`] function returns an array of [`os.FileInfo`] structures. It takes the file's `path` as a single string argument. This path can be to any directory of your website (i.e., as found on your server's file system). Whether the path is absolute or relative does not matter because---at least for `readDir`---the root of your website (typically `./public/`) in effect becomes both: @@ -27,7 +27,7 @@ Whether the path is absolute or relative does not matter because---at least for ## Use `readFile` -The [`readfile` function][readFile] reads a file from disk and converts it into a string to be manipulated by other Hugo functions or added as-is. `readFile` takes the file, including path, as an argument passed to the function. +The [`readfile`] function reads a file from disk and converts it into a string to be manipulated by other Hugo functions or added as-is. `readFile` takes the file, including path, as an argument passed to the function. To use the `readFile` function in your templates, make sure the path is relative to your *Hugo project's root directory*: @@ -48,10 +48,9 @@ If you are going to create [custom shortcodes](/templates/shortcode-templates/) {{% /note %}} [called directly in the Hugo docs]: https://github.com/gohugoio/hugoDocs/blob/master/content/en/templates/files.md -[osfileinfo]: https://golang.org/pkg/os/#FileInfo -[readDir]: /functions/readdir/ -[readFile]: /functions/readfile/ +[`os.FileInfo`]: https://pkg.go.dev/io/fs#FileInfo +[`readDir`]: /functions/os/readdir +[`readFile`]: /functions/os/readfile [sc]: /content-management/shortcodes/ [sct]: /templates/shortcode-templates/ [readfilesource]: https://github.com/gohugoio/hugoDocs/blob/master/layouts/shortcodes/readfile.html -[testfile]: https://github.com/gohugoio/hugoDocs/blob/master/content/en/readfiles/testing.txt diff --git a/content/en/templates/introduction.md b/content/en/templates/introduction.md index 5d60e9ed1..93666de28 100644 --- a/content/en/templates/introduction.md +++ b/content/en/templates/introduction.md @@ -301,7 +301,7 @@ Below example is "Example 1" rewritten using `if`: #### Example 4: `if` .. `else` Below example is "Example 2" rewritten using `if` .. `else`, and using -[`isset` function][isset] + `.Params` variable (different from the +[`isset`] + `.Params` variable (different from the [`.Param` **function**][param]) instead: ```go-html-template @@ -355,7 +355,7 @@ The following two examples are functionally the same: ### Example 2: `index` -The following accesses the page parameter called "disqus_url" and escapes the HTML. This example also uses the [`index` function](/functions/index-function/), which is built into Go Templates: +The following accesses the page parameter called "disqus_url" and escapes the HTML. This example also uses the [`index`] function, which is built into Go Templates: ```go-html-template {{ index .Params "disqus_url" | html }} @@ -569,7 +569,7 @@ params: sidebarrecentlimit: 5 {{< /code >}} -Within a footer layout, you might then declare a `