From 24a61071716a685cdc82306e69e6aaf01ccf49ff Mon Sep 17 00:00:00 2001 From: Svilen Markov <7613769+svilenmarkov@users.noreply.github.com> Date: Sun, 9 Feb 2025 17:33:20 +0000 Subject: [PATCH] Update config docs --- docs/configuration.md | 770 +++++++++++++----- .../images/calendar-legacy-widget-preview.png | Bin 0 -> 10835 bytes docs/images/calendar-widget-preview.png | Bin 10835 -> 13174 bytes docs/images/custom-api-preview-1.png | Bin 0 -> 8068 bytes docs/images/custom-api-preview-2.png | Bin 0 -> 5826 bytes docs/images/custom-api-preview-3.png | Bin 0 -> 21811 bytes docs/images/docker-container-parent.png | Bin 0 -> 17836 bytes docs/images/docker-container-parent2.png | Bin 0 -> 20362 bytes docs/images/docker-containers-preview.png | Bin 0 -> 34236 bytes docs/images/preconfigured-page-preview.png | Bin 350979 -> 371001 bytes docs/images/server-stats-flame-icon.png | Bin 0 -> 9864 bytes docs/images/server-stats-preview.gif | Bin 0 -> 204897 bytes docs/images/split-column-widget-3-columns.png | Bin 0 -> 149054 bytes docs/images/split-column-widget-4-columns.png | Bin 0 -> 185117 bytes docs/images/split-column-widget-masonry.png | Bin 0 -> 333240 bytes docs/images/split-column-widget-preview.png | Bin 335405 -> 347141 bytes 16 files changed, 584 insertions(+), 186 deletions(-) create mode 100644 docs/images/calendar-legacy-widget-preview.png create mode 100644 docs/images/custom-api-preview-1.png create mode 100644 docs/images/custom-api-preview-2.png create mode 100644 docs/images/custom-api-preview-3.png create mode 100644 docs/images/docker-container-parent.png create mode 100644 docs/images/docker-container-parent2.png create mode 100644 docs/images/docker-containers-preview.png create mode 100644 docs/images/server-stats-flame-icon.png create mode 100644 docs/images/server-stats-preview.gif create mode 100644 docs/images/split-column-widget-3-columns.png create mode 100644 docs/images/split-column-widget-4-columns.png create mode 100644 docs/images/split-column-widget-masonry.png diff --git a/docs/configuration.md b/docs/configuration.md index dcfa355..0cee1ec 100644 --- a/docs/configuration.md +++ b/docs/configuration.md @@ -1,8 +1,12 @@ -# Configuration +# Configuring Glance -- [Intro](#intro) - [Preconfigured page](#preconfigured-page) +- [The config file](#the-config-file) + - [Auto reload](#auto-reload) + - [Environment variables](#environment-variables) + - [Including other config files](#including-other-config-files) - [Server](#server) +- [Document](#document) - [Branding](#branding) - [Theme](#theme) - [Themes](#themes) @@ -21,10 +25,13 @@ - [Weather](#weather) - [Monitor](#monitor) - [Releases](#releases) + - [Docker Containers](#docker-containers) - [DNS Stats](#dns-stats) + - [Server Stats](#server-stats) - [Repository](#repository) - [Bookmarks](#bookmarks) - [Calendar](#calendar) + - [Calendar (legacy)](#calendar-legacy) - [ChangeDetection.io](#changedetectionio) - [Clock](#clock) - [Markets](#markets) @@ -32,90 +39,115 @@ - [Twitch Top Games](#twitch-top-games) - [iframe](#iframe) - [HTML](#html) - - [Docker](#docker) -## Intro - -Configuration is done via a single YAML file and a server restart is required in order for any changes to take effect. Trying to start the server with an invalid config file will result in an error. ## Preconfigured page -If you don't want to spend time reading through all the available configuration options and just want something to get you going quickly you can use the following `glance.yml` and make changes as you see fit: - -```yaml -pages: - - name: Home - columns: - - size: small - widgets: - - type: calendar - - - type: rss - limit: 10 - collapse-after: 3 - cache: 3h - feeds: - - url: https://ciechanow.ski/atom.xml - - url: https://www.joshwcomeau.com/rss.xml - title: Josh Comeau - - url: https://samwho.dev/rss.xml - - url: https://awesomekling.github.io/feed.xml - - url: https://ishadeed.com/feed.xml - title: Ahmad Shadeed - - - type: twitch-channels - channels: - - theprimeagen - - cohhcarnage - - christitustech - - blurbs - - asmongold - - jembawls - - - size: full - widgets: - - type: hacker-news - - - type: videos - channels: - - UCR-DXc1voovS8nhAvccRZhg # Jeff Geerling - - UCv6J_jJa8GJqFwQNgNrMuww # ServeTheHome - - UCOk-gHyjcWZNj3Br4oxwh0A # Techno Tim - - - type: reddit - subreddit: selfhosted - - - size: small - widgets: - - type: weather - location: London, United Kingdom - - - type: markets - markets: - - symbol: SPY - name: S&P 500 - - symbol: BTC-USD - name: Bitcoin - - symbol: NVDA - name: NVIDIA - - symbol: AAPL - name: Apple - - symbol: MSFT - name: Microsoft - - symbol: GOOGL - name: Google - - symbol: AMD - name: AMD - - symbol: RDDT - name: Reddit -``` - -This will give you a page that looks like the following: +If you don't want to spend time reading through all the available configuration options and just want something to get you going quickly you can use [this `glance.yml` file](glance.yml) and make changes to it as you see fit. It will give you a page that looks like the following:  Configure the widgets, add more of them, add extra pages, etc. Make it your own! - +## The config file + +### Auto reload +Automatic config reload is supported, meaning that you can make changes to the config file and have them take effect on save without having to restart the container/service. Making changes to environment variables does not trigger a reload and requires manual restart. Deleting a config file will stop that file from being watched, even if it is recreated. + +> [!NOTE] +> +> If you attempt to start Glance with an invalid config it will exit with an error outright. If you successfully started Glance with a valid config and then made changes to it which result in an error, you'll see that error in the console and Glance will continue to run with the old configuration. You can then continue to make changes and when there are no errors the new configuration will be loaded. + +> [!CAUTION] +> +> Reloading the configuration file clears your cached data, meaning that you have to request the data anew each time you do this. This can lead to rate limiting for some APIs if you do it too frequently. Having a cache that persists between reloads will be added in the future. + +### Environment variables +Inserting environment variables is supported anywhere in the config. This is done via the `${ENV_VAR}` syntax. Attempting to use an environment variable that doesn't exist will result in an error and Glance will either not start or load your new config on save. Example: + +```yaml +server: + host: ${HOST} + port: ${PORT} +``` + +Can also be in the middle of a string: + +```yaml +- type: rss + title: ${RSS_TITLE} + feeds: + - url: http://domain.com/rss/${RSS_CATEGORY}.xml +``` + +Works with any type of value, not just strings: + +```yaml +- type: rss + limit: ${RSS_LIMIT} +``` + +If you need to use the syntax `${NAME}` in your config without it being interpreted as an environment variable, you can escape it by prefixing with a backslash `\`: + +```yaml +something: \${NOT_AN_ENV_VAR} +``` + +### Including other config files +Including config files from within your main config file is supported. This is done via the `!include` directive along with a relative or absolute path to the file you want to include. If the path is relative, it will be relative to the main config file. Additionally, environment variables can be used within included files, and changes to the included files will trigger an automatic reload. Example: + +```yaml +pages: + !include home.yml + !include videos.yml + !include homelab.yml +``` + +The file you are including should not have any additional indentation, its values should be at the top level and the appropriate amount of indentation will be added automatically depending on where the file is included. Example: + +`glance.yml` + +```yaml +pages: + - name: Home + columns: + - size: full + widgets: + !include rss.yml + - name: News + columns: + - size: full + widgets: + - type: group + widgets: + !include rss.yml + - type: reddit + subreddit: news +``` + +`rss.yml` + +```yaml +- type: rss + title: News + feeds: + - url: ${RSS_URL} +``` + +The `!include` directive can be used anywhere in the config file, not just in the `pages` property, however it must be on its own line and have the appropriate indentation. + +If you encounter YAML parsing errors when using the `!include` directive, the reported line numbers will likely be incorrect. This is because the inclusion of files is done before the YAML is parsed, as YAML itself does not support file inclusion. To help with debugging in cases like this, you can use the `config:print` command and pipe it into `less -N` to see the full config file with includes resolved and line numbers added: + +```sh +glance --config /path/to/glance.yml config:print | less -N +``` + +This is a bit more convoluted when running Glance inside a Docker container: + +```sh +docker run --rm -v ./glance.yml:/app/config/glance.yml glanceapp/glance config:print | less -N +``` + +This assumes that the config you want to print is in your current working directory and is named `glance.yml`. ## Server Server configuration is done through a top level `server` property. Example: @@ -185,6 +217,15 @@ To be able to point to an asset from your assets path, use the `/assets/` path l icon: /assets/gitea-icon.png ``` +## Document +If you want to insert custom HTML into the `
` of the document for all pages, you can do so by using the `document` property. Example: + +```yaml +document: + head: | + +``` + ## Branding You can adjust the various parts of the branding through a top level `branding` property. Example: @@ -1016,65 +1057,261 @@ Example: ``` ### Split Column - -Splits a full sized column in half, allowing you to place widgets side by side. This is converted to a single column on mobile devices or if not enough width is available. Widgets are defined using a `widgets` property exactly as you would on a page column. +Splits a full sized column in half, allowing you to place widgets side by side horizontally. This is converted to a single column on mobile devices or if not enough width is available. Widgets are defined using a `widgets` property exactly as you would on a page column. -Example of a full page with an effective 4 column layout using two split column widgets inside of two full sized columns: +Two widgets side by side in a `full` column: + +glance.yml
glance.yml
glance.yml
glance.yml
glance.yml
{{ .JSON.String "text" }}
+``` +glance.yml
glance.yml
docker-compose.yml
*vhOK+vS;u#QLv8N=-2x}-mE&TY4D31$LJ;QVKwDO6JY zTG6z@ljv~_Yx~SPr;AhT&+^k}U)y&Q; k4 z^x85&etn#`bInJ{GN!iEUTNEPFfi~+A7eOw#Srqbzx9O@&8aF=)pMrU`Co2 *?<=EK}a{lGu_1z#k&uQ!*}pFNHdY>2?4o1+nD zO#Csrd9&&>F(T~ZJOLKVjD2`%&nk$Q3PMEN>wEYKPJmkbCQQM;hT+K7_GF-r2MyZK zK2|uLZqtr=yDqiX{pNGF?O^g*fOm`WO{3INCSg}-kU{BhA@hTQ{kSJUS=|0Jq?h{O zPp9yOizS>f&T%6(6KY}Mw;e6js%y`VcHq#+pF9@51nP9dVr+h+@K8S;e%~a;;Wyk8 zq;rPy^CEE)Rpp!Bkf6&0t?s^DBTxZv+0*iz7K#OWwr`Dt&7kpP4PgD3)uTlqVxZDh z817$knM!nI6!QIJ=h;ByF{wFzIU?6p0+bwczI ?fkjjJ906EzI#1b@$8~1)L;5d*k!jod-6U?Vt0$8h0wK z7O+~tr3(5LTSuU`6As3wYHcqbiWZ049hD{8>Q>JKNMBl`#tKmRQ_Xc9r#cAVFRXP; zVj;V+w5N-$pP`vPNOYGzajCda+nm%`@T_wTW1JC_5KuG>G`X<+up$5*GrzhGZsF?O z@SCIq(=|ch#HC~C&u~fbjrPfv%kb33Ni#Yo{-tY% q%wPlJ15a7>eI$^|pEtrdf7(*%OkQFl&2SW#}?H*f`rWQuxegtFiYQ#>6Jt z83-6Fu)_}1+t}-qlpTAslQb8p9E_kT??+1dJyM_A%j>^w GlrFjI;Tg)XvWK=9T4@lMFI+#`X8WyqCSc z>c$^$RSkR}nAS? H0MDJ%dN>Ua<$Vo0XMRQLBHiZ|bS1l=PwJoJSaM)dRQm7~>)qKEQO zznmPR1|}a^RdS~~QWb+J+6&H&HmxY!Je4abES9R@v;}{;EbIZ{r7o?~Qd5%BJbk+9 zAoW2}WbV=So}RNqk1{Vu{%G+Y(kC|C0@drM8&<5aCK@L6unECg9&aG(0dVv`W&Pqp zJ3GCNr(aHQU1Q)Ul$N^`QCutCYn%R|QFI@NZ;2;m4nIJg&C}yYvPlfwok8M9==M_R zyd?cfPs#Jd@(w$Jv<4xgEN=HogWc3##e-z`8MX}SDf>8b8j{X3Qfv$D{032c)#1jO z6b{y*U!{J!sO<}m*!(oj970_;ORh<#{^bu_N=F{}tbVXB6rR4?iGAT^HcCIfcjY zz6`^+-spNgv9vtRSXUa4`Vpc4FjUIUP(6+IIR(Y@wbxlFiVeHovGI{R$>~PZDQq?I zvM;T!J_NXp!ZN?TVgx#C@9KKN#>Z=w_@uwY>)V v%9(XmSDr6elCEdVY1>UbLVcW|!;Az*zk2&si33tlY|pZ&DEdf(k}2L? zj5a^ciiYMq!=--9ipWeZTf-!Ng`9HPrRYMD%iY!mb !;THu4RsMRGUeHE||dKPVLWg+)jQN!TeWXa<8`&La3DIsu(^+o!n z3WSJ&V72$aA^5Ro{2vgJW|pKR)^n2MbzH2Cd;fKu=|4fNLVdZ3lj@bT3VNayx3>~T z*A{w8wM}5!f2cNRFbT~gku?OJ9X0jjRXJNq(;V|Hud$=X%f9lh*(|Un7luV-p(DkT zDWpyV%Mr{&? F2E3U zd^sVAe3@FBqhIbP)D|L-P8chooo+ZX;P2JXYPz59JscwSiRifa`=6!}k^1`d^cc;+ zT7zsy&Q{mnh6HUbJwro1_SLCJd1JEtUur%LYsEWkldZk07#bXS+Z9H`gcnm>k{)s4 z?^x91MMzk=%`r64!vTytlue}mHK-fYVO*v$uV woNjZzps^u7 zmTCe%l523J$Y^qoFp_g7VHYdF5vkhRq7SI6$uE}jqA^=GlrO(TPaCKK91}nLYA;7v zA6A6h(p((^t7ACPw|~MUM@WJ^&{2!l8NKwd9h%9S_O=lfO;B}>;>gsLj;0PfFSj;W zf| C zmaXI$iCNcp)%WFx4Iwm|`rmi-6m&T=qHWeUhl=Zy0LAq`zt`8lGc<}TGVCg?vMn#t zMXYjkD=EubVK*{xUT9hHGB;=X3H?gdzpip?hxz&ep}g$F+6h(Qv$4qF$mn0v%w@0j zUHQ5-C@jyns}S^L0=al1bA^q{83$>zd3ij8k(n-bgZiU-Psh#GlsoH^1aKDmq`W%K z-|%MRlr+~W-aP+1+eE4EuYDYYZ^zm7J-JiZ_+%fImw|r RU}Xyo8A z1VI*KAAM%6BVFiucO^vMaC_uW*QLL`^bFA)>*BlCIhShRmeRSgbt6s5a$j<>yUOj! z2qg yhr@KR?B7Nm>LfI& zcZrw2rCVUy@@SMMdq@>TDgR>G?#-aOVj0!`DVfmBhjbvzBQreW;vVlBSe)M4nqbjs zSiiecdUS}|ms4LVON!Oyoo%v}#01Vi{GML0 U{7MzE!`|o^6&Y>>;`%ZV!Vx~rgAC>6u2ACt7zsztARofz4LIqYNzmq}mB0zM zMbjI{?Rad_;?UkF?dmJ4`1^|y9;o6!T}}dFg95gNX|IZqPEKVTGOmQcqDjNK;UUnm z*V4+H0C`s?UK Xr=E#72aPl79 ziu1K^!RHm&VayM2Uw^p79KB9*-IzYa%Y I_MmjqZRq#)WWuPoc5tl$He?WR0> zc(zYnviQx&G-_+&gBWN*8zcN_FVRAyQ*K0^gK|YtVz`{(V}xV$lHi}*8!W76|24`0 zXZ`g42P$f!iH u<2)6kc)(3c@TaCuNxE 7vj68uj@N8fMtLkb_+(e$e%u*@2XfvbgF^L}r2+c|7rT )HvF=5b=7sV_nkk!e5Kic?M?TJq|T<#gy3} zM=?JW&h~#}AqgCdQf|-ijpi`48ai;TqwS+sCHT_Ur{(F|(dCl>c~!Tums`(u1F(Gm zJ|N(|V`INHvG1B0#yW1niDLbvgG#xq96cK(M?5xbC-%F($zcXj+}Yu(@80=r1XXzH z>A#iQE4u)8&q*7FXN8_c%Myh&N}R8O#_nYT-O`pACC>Uoo;~w_V8|KZ9LRU&H+yOl zR?d8FNfvs YhQ;n$tF(psd9#~KJ#{oxjK>y^B-*^Kf6RFE6Lw3*VV-~bR%dc za~g>imA#~7Wu?jtcUF$hd!f#g%3BRN$z!?wuVYZem@KH{FAhb9mXtK3HxzU4aNSIs zes9Vd&lZlWHY9>-Y9oRC1e4ER{F(mdvCCFZ_kl<+Uru)2`#VCPe?TIRtDjTF1j|Mc{NhAzlMH*fh`9lpA?p5Z8d)ob4v3|~2( zv_~FgoA{r0>`tA`g>eqnzPGaGF{yE?%h2uE%2?RF@Y#K)KO)*sz0h(wc!RUmm|x8# z3M=SHY_>{FG~#f>H?@r7qy$Y9(goRQ5~WE$!w!q-6*WSB%`;(HPkAyu74P$~WvW8J z=JxYEBU?caPPI4{hZ) $-O_x|EF|B8i?JYxC+IQq3?RM zP8l{U%9-N5WXw?y1XswLMSg<@py$p`8S3iiZuSG#x8N1ua((GNOb?H5)~5WyYK*>M zB~5R3sHp$yQ9m7kk258m_N-N1-^*tu+OirBc*5nX_fZ+B=BW7`G!4J?s_?fO$>cSB zv+yQt@HU%1pvmv#s6;>TgWMha)q=&RKw8lm^|=xVrsj}B`3)n(1 yZjP!TWGB!QZWs@Y}CFG!#KRMC!K0~eG@XqY}c~@t;)RVo3>vKshD4=aho{+ zKuKIH9?5z1xZ9#RCmMn?eb9~2pxeWXRBwZ!kX)Iwmv1H?To$9(YQ-wQ^*mOM?*MwI z6pGy@ANdI_k4u|dpkHrH?YkuQMQ_k!G@E8=3{+3Vp)Q9B4UDu4&s5{tHZr+pMp(fK z&_HDHREw$|2(6~Kdqj7AUGYAusJiF&V~J38;NWx4mIE-=nO$E)@et-RIUC~&YA1sC z-T>j}`xYR+PF`Ct=3b}Q5Fz$y(t_#x3%psVH;T3rCwoQ^oE*GBHmeeyNW+=4fFs+j zU3;WK0rYW3+#^X-O+av_$V9)W7lu^DuIyX1VfFQk3Cv^#EVomHcPB8&7X}<{drRkH zDAj0wn5aJBRjN8Gy?6UT+0Ad{$Ac4nmxF`OrbY9WdsSx_ok>zhxdp$%qqYo!AmZ*Y z<#vXI j %Kr@shDM+1X|pw%Z&gKLz%v z$djypnG!IIm}wDA{S(QOe*`s +oZHsK&wq=1w9VP$$ipYyN-d7P z L(w45(@e5O&_?`GZ+ACWTvuM+k9CynPE(iBC&bnXj95h^57%2w7~JvJ kyao1002i` zoDzxCJ#4uQGa(yZoO}$69w?NzJ9rLXP}Mr@9(vO5x@~KE+TVyda}L5_R>^m^S>Scx z^!&|3GA1Qwap~}_;Nl-SpVNIiIjIB#(&Yoz$=FE>aQu|CPSGuZY(UpP#&a8`GO$R& z^0_BF$v;0-MK&QVi&$F|t~%^x5xxY!IO;+yM?DNQcAsQRt$D1 HKX=r+^#QQZ&K(X!HS!|Aa7Rg*Z*%;cwDRWHhN{D1hH`f@fn|kg#*K!Q54hL& zXs;FvOn~dzMWQKV36n2#sgl*Q6}9R`jaX-VP bqTe|Yp z%j4ZSZimK`W7UJ0UEL7O8&0+wIbMa8lXubDNF=7|@Z7@{&0b}4+}F2hANnfw!xBPh zzZFx4SrbZY(B_ubFE{!Vhv`0(sh|pbs5*=%5UV;YZ_yS)mk4|D{1?JDJf$USK7gZU z38rckyHx~bzjxP&=Wipcdm&~c%vKaf!(W)Y$$`$afr2vac65#2gZK8vD(Yy9 @PCgzp)R1^Uwx 1sZKG7*dpQ`f<`9uQHmMYEY#3ZB zmrur>Z1k5Y^A-A{?S8~_8NyA~V7b)FE^b!uJbNDaEL*< |4INZc7Jh1u0S3ZmF@%AKE>ew!QYwG`Y+ z_iVm;Q#PqE*(*D3s++$Xygn|$H5F--=fv9b3sZt#iI`p CW>v{{0*)i{Srl^vOS{0Ha3oyzKTFq5U8;ZO&OqdFWp4^jSi- zAvmb{Mv(oc+%x+u^3;M=Uz~JlKwsRm>$Xf(gNbK^BdWOebwo4du{A~SZs061dSX8} zJ!Ky`hqU4`RQhpG^+`9M`|esT@_UVEM&;Amw{1aGY-@IRYg5245n*q@@ tHF(1hAaCeS|8g@-}C4<0+?R1;xJo99&y&{Q *4PL zCp=HB*H6Ftv ^lSyj3BDP6CuHFD|=l3Jv$-@a_nFDQO9`7A7Fp+ypD*Z6sKzFS(4{!Vw^tqpB) zj;TN0w&lH0$^X @dfaJ*DEA9onelh^^w!Ok^h}zBF?V|*;rby0w39U# zDi~st5kER$nF8fMt0H#Iv-RVwQjO8{T>AC3kE{cppC41NXoMu2ml1nR^oH CE&P%W2F6S&H%PR^oFQWq16{l}};hpAoJ2j=Q<)P($atb8W+yCPsj|F~Vo%FBzAp z+Nb@?L^{g#ynfaa`)quxr_BgS-P{oDa{Oh}QEHVeJC&3n=@Zj4CV@hScqu!3oCf*l zE9P;OIT)(jqF1t66Q-^Vlx6S!L}J7Ef%)zSX&NSe2fC=XLFf?r{9=_j{4zm(<+NF^ z@sY%;ZHkR`Xz9ftSs35)kl6^iPUZRw<`K1zNG(n1zjhk8pKkAV;4GQvCeFv4zkxIF z$o?;5+x`>G@qd=o-t@7cZhXjbppZ<$SC1Ss-YCy9{0KX=oczvzG=!Efeh~oBx=`qn zF=rZ9@0QV|%9!T)^hD+fNK8~k)7QO1M|D-55+B!CfRge}`tJgW6d3crMZqc*e&=|x zGI$9K9+p_o*%K-5b&$?U!^Gv9GJULy#!fP35OE9B6duq6to6fuXUP&j_7xawy(ONM zD{3hzp5kPbH!-RO^GAk1zM?EC(po@*uHkh=4C2Zh;G;(1X+1Wkc<$t&s{5HRCNYfp zICJawTZAHl#W^lrRJAI5Oa~TsSTw#(tCG1XRG!FyDI z$J$8WgL?&3Zf>c80^Z?ScZWR&@%OMF_|kRV^Hw%J{LyB+tgi+zFih*+#>Y<+VfYIR zdhtAOp-8hTB;>xHo}o2D1o2FlFQSEVsMv{6_EZ0>PxoLLfb>LGO?m4*Edd3=)>mqk zjU%?$a_?04e+*XEDaf 8&Si{Y0eTgrkdV=qS>(fJ>=nN_j^;yu*())?}(Azy72?UrD8Tcv8k+JN( z>B )dhVOO`bzsBk~_*H>dI$#vpKYsUdfhmF9hVfjgt%p;cA#)xPHg zh5dOgAHW+>!>(3~+hX^wK>pqx-?FBSZaFb{nf9^?dH96H=!e$8bj$iMv o|#gNUjHjMa+>94brm2ZsqK83t9 zS4tG{ii|=faxfIa-J>9!YdE-6WYkKd)J2rl*{t3X?4Q@<)!m+wja6RL`u}lB4psIa zT7Blx0p5rld{$Bfl2_N&)tN?sZTjI3yq5CJ*2;PdElLK z1N#P9lE}F!d>lmNyp3+TgT@430X&H%c4fvq4Sj-tYP+~Bw4`mw^*_{ky3jGKy>cYg zuW*O51tiCP@VDa29#2V5(Te(uiper>GLcC|x!lFi0zCgea;QA}1U^JfuZxAyI;5%k z=FK6tOHV~owcTFjCLG_Ezh59nNRZW!&G3vkOSkXNjA*-0E4Z@1IgB~p^`|i-Ow`LW zdCPb*QWr>NEBFrw64#vKSK)(u2SrKGk89|f=>BCUI9H6)yakhz`4jJusBRBDw{@M> zKjT~3X%V$lxr_&LEsop=M$+jy%EU35_N03f0)xUumj>^nU3WYFp*L~>za5zoaxcp` zieHs)9+;~b!MSk#yj*PM+%jfo-4cci8yZqa^(c+Ie?Mv5TONqssd~t4#@G94#&}HO zgZvcs-fz;mKu=cdgdw$v=*^AIfpSH-j?x|GM270s?I`5zL#gu{!`?@7=C3g_!I1ac z-1ZkIY?9*OBl_Abf2uNZbW#ARUQs1my=6{L13ZpJ0}dM+f&=C8?!NSb1GY1Ow3;Lv z5?C?7GkNue;4u5n1N+QRX^*b1shPl%1$%u|tGk!J1w3Wqvnpvv1SfYe(}0zlwY7@1 z%<&6#s^tcEpgdXq^pQ|b+@q!(*!{53P(|&;^shSkhDg+I=|$u;OBKjz8ZiALfEAat z#a_<#J%OG-@cA9Uq#H(S;~JLfQlAsmYMsq|-)1rW#?e-dV~tG&(TW_;YtB#Fxp|vb z1gUu5%p$5>y4d(-mO+bjJbu mcfPjBsjc+87#qoIt@EGq8{Z)*B9oA!B8Seg zUB=Uvq3`)hm6>T3AE*OOCcQ#BA6uiH6)1t+jV~pMK}_;Sa)EMkioEp|MFZhX?sYsa zz$c)$F$3S5#Ru}fUDOWdwHTpy27_uZqx14S6!kfhS)EO&eeL7ejB)j;N(ErwXESPp z8vfXShF3FJ6q>dQ!rt@tysm-i>XCd?Z2akBXd>nN9HnF(X&WB{baoig)K|N`eSw-5 z9msCvJMy!1_si^f{c>3L?AvV5D9O5>7s2OzxeghX^kws4ew}X=KDqOF$GT?nxdwep z2~AX;9#7J0^j>UM*NSBH3fLYy`LL3h@KN>}Es62cHfv8GZH~_&$9t`-kuQ253<=Dx zrQ!2Hjvao|?6T*5tG`e!4!o`UKEh~~{d|h (6 GZuMmvs3C~Zx_K>#8P#^(Gq)o3J`Y+ zvmzht8jmb5h_M*sIiv~HMN ?o*Wx3YJ-ycINR#6ltJMjmF`4imnr)Rw zo?hN{)z-=^u7AEJ2D~NQZc8p)mm`}L<}&J$SezJRbopT<)Y$NA+K^JY E zCYNhEBv*g`>gYa}+`a#=dhZ_`$qFB=pFGkN9?N(a0{umvnD}MdaBoUmh0a~*#+^^O zf(4 e#`KW^Gjlx2mfz4*MI*T3%vGQx|h+fX-9S?-~Ro0L{U~vru@Bm@c#g^ C9<_V` literal 10835 zcmch7Wl&tvnr#CCf`t&=lMvip8-fQKcZWc53+^<*-Q6X)1=pr=*C35`2=4CwxO4AR z&5xO?nfIpNkF!qgUHiwWbN2q$`qo)tN($0g=p^U>002woi-ZaQfMD=)A-qO>nSsXX z*uUHmoK&R609E5;yDx)R=A!bV06 Fp_iw-VgeS^C9tjnA0f6ntX1Oi*0^B-kKgemm3wQ;DCB; z4aE)&E-q3a0sQ_D?K~p@a#2H30089wJqW@%V^$P{YO_k+E}o^4sOw59bWflmS6X0< zyG`v88JZ0Zv0@jND&q$uLoO8D;V~=yn)$VF3`Ba!;V=gNmQy7Xn(W8DHMT$S0z=A) z?i>jrpE2Wz2npa5tFcJhs+h1!flaxBVrazi0-yT6!nC12|D2jv&K@dC=Sftka=`2c zp}B|2t$E||@-2KpC4t?EAoygGCbKOBV@?Uiazz%zKvBZwvb~iBZ&FPw(JAfJLu^kg znNi)Z4Cti-KQ#CS@d|??%g~S-4C2asd=If7!~$Q>BAvJs;Y|IdYfK`{6alxXFjTga z=cv8sZE}&!I6-PJPc_U+Q;BMEzo5Xvl%r1I`O;=@i>?+m%U$mtMLHl|NYRSN+)Gtn zhx^WHX$<0Hqx|^3vi#fP_5k=V$P`mh`mh nzhof;3SZV({7~S9gV?AND=is z{Vd !Fro5b9+7v*6P31!p zzkB#~Nkxw?2~J Y8o-Z-M%68FbXAiQN2?PX9^PWoMco)-7RbQ|BNYp?(U!bbY6y#c1Tf)I(9oESm!g;_R*Zw zV6(x;;&rS_zvG4bP7FOtZbyQuG09t_AK^aisZyy@mGTK877(gO9ULiO1Dc;GDbAFV zfp*VjI(v^I)4Q-oGigtU46E=k&+MiUb&$3wHwofK3hcBu`&tCZwuUZ|{1HAj(|kWa zwsu`Yh{ji<1InVN-xB1{8+lhB$yd}%b% 6@7TDh+PviR@kI#T~ zlKQeUl)$GU({8_%IW;S_PKOi5549ac3~7a{jXc{zlenqjgxoU6Ne$_OEiTxsfuc^D z?G0jXx?C+@9aA1EF?aZi$az-eGM;v*1uzW4Xy0h}jkOj7hW69xZxPs5`o*7^3%VR_ znguh}{07h~JkS8SY~95l5CAbK5-?@&6efS74pSHED7*0SJb+h@IajEoS(VWW$EJ z^7u*SZCEHU7?Mby9hC6_pL0%n*dqGW%DH6=$<(KQjN_s^ws$Jg;l*MAFiE}LdfWuO zVLfi2)g(~`3J^qMItMUH001JXo2rmwzmm`Yn53NVbVu-$MqIhv$@&|hNCyDmy(jr! zgQt-EuH^;T0vQ|?fO!O_Au;A5yZL&Ljmp!T%K +=}^0LxdBJ-A(emizZLk4q~dJ>E)LzMGi~4PLwspvv5HjE848=7n_UR5CAl zEjK=TkCAt^cA&HC>P4LEC*9tJhih^E^Ahg1HQdv$xs4vo52$S-LO;!8cR0M@ i;Ke8W%#1Jm8bW*lCpDPyQp3dP;P&_&AY6+LY(6k_|rx(f8 z*Uw!A+>ZHOFqk$S>o8D5Ei4Qu=IKg$D=gS 25=NmY =ylFE*{q4XEt*6;h1$`WKDsH)CFFJr3!rHWLf3fNf{nR<>SKof^My>9Xr< zosH{W5?nF7Tx?q@a)| t>ZOE5DBA$^^$KWFmq!BWl|cUILxfw(u59 zYuq$UZ=p7N?7Gwue=Lz4h0ePBrn(T`YmxN$0|H+kfz!XOLy4qqEsJiMxA*az8R+;W zh;bu28T;j*bPmu&S 8zT0Dm0lObCG7dO$nweK?+Qf7(1k6N0?mo{fx=hD>+8ob(wd?3OrH z{J*}EL}H&(O3u)W(vM3V3@Yfq&ayK~c|6-H&+)0d&zLYUtYy_4!%n? m_)8NC3Wbs4k!%G95yVc+`0Zy*tRq zoK?ENeN@+-PFKnc={bJzSV)02Tt8ooesegVRh32o7j>!o+&gY?QW{E7chKh)Xbih3 z(j8lfUb7|XM4ie>^unDednKwC3%nwu(6Ch*1eJz-r_zxN(%&`NkBj0{b$tm#G0xAc zRErN;0ebCIm>u#IO{iot&jz(7robzcjW?!BLu$KMCV>Y{ZKgzK6^}uFU)A-d>A0HK zGtj 8IucnVxPq1Jy zKE73c$9u)_-(#DF*V)&$q0j9wvNOudi-c9PB*GXMsO}wZGjgz`q+BGXBR8j*dO(-7 z_{6I+&Ujx*Q~v?$HeZm?Nz+@kgAvoAVY;Q-@?yJK>L=Xl0hIb;@AFI3hX-r;S1#%E z!Khe^_p~HucG*-%BUOLsd-SBGv4x$ O2{$u;}Cz9PFxXy)bsls7Wfw z8dTF!#EjR*EPB5Ng#VlvP$pOe`+X&&K{^iwhSCHmK<2$r78&l&H-17`@9ICKScZ>W|wEOl~;my>LuH_v!a9Uwncn*`O)c@8@CG8?ZE;4 z^pI29>ZOx>uPJOwi-Fe Ol(9U=|2tY+H&UIKUT$ g^rJQS zSr}tB;n{4~nlxd*f|hj$oPN4e2ln-RpPcmF=-0KBu8(B7Y=BGY5~ z_(P~J0yG|bFMRp*pk!#cQfhCr-0>KIJiY;KcG$B@>+3DFm+RvV6gq#}Iy9_G7qi =h&p|dH?wU}O3-dB?y*>|2^&|66U(IV_y7k;wxvn)?!p1ur zB5=W?{ziDxV|aH!{NNHiZrCKWT*36n>p0V!^YCZ !68Ozg4{HNfbQ*`jsIji1?_v27_>6ZA z+w&VY@{Zq^l6@j}&={$2Q7n;&=Y7$5n|!A+G8#} zeha|%L)(7?7KU&>txxk*vtTu@8lSah20ZIE6?@4wegmCxJTJrJ><^^zfy@i>^~;p- z J~>Tp;N>_@ zi;4c5v~$V57>$0(b9{=P5$-!tO?WRkKWivkEg6$X__QG`R#*nojn~{T!@n}b&CrlS zEH)CUnS9-o7}ey2Zk1SKU>`Y}`7jWA>mE?n-@T7~iLNHXw4 DX=AFff+pA70DlK@h+{@S~VW_j!i;bgyMeLN)2?T?qz zDK4$LQ|-sd6|H_pZm((#R*0N1XK%xEf6{ICsvGu&x-xI-cp|S%FChXos@;e8K$ft0 zJMQ$BR!mR;k)f&^zCC+E`0j?E>qpN)* FpWn@9o?^#oQU--QpYpp*tPV=6&m&XEM_bNTj1*Tv8`9F|lp< zv8OZ`b?fR)r5*9kBn`to>+lAU)3>1&86FuL8vXhbk8OeJLJMMLZP}0Qsz1hTYxCw% z-)c1oN^n+03SRwY%iO!#P*B?1lJzG6Q?l}vqPmPJ?a~yuwh5X2*9@DSKH?Ay`F8*I z8WNWdJtH;DSCN%&_gmXt$g5Z^5(cDj6qJ6Y`k7g`x5xPdu{xz(YZz&c+971?=pN|` zhuT)=k{WA;pv8=AGt>}O69iA@Fy07VW&NgPuXsoLRz(bykP$PhM0qUy_=7b9kgni^ z++-KL6(|z+Kx{X?Nc5v?tA^Oh)Y?{Z>T-?8T9;AHJ`~eqvOujAIr-xn{&zV!t#AcM z^-8r``8 @%(EnWGGHkIzHk;4cS-tlO52 zPq;pdrdc-8I&;A;&Kxad$hYj@O{NYB&K*|2#;uB8Wl>AYFG~A|%(!nW1az`;ad6qB z^H%FQVpCFcCF60Y-%14sDWKsET0UDe*U%MreUr18PyD3>HgK7P5WH-~9lHdN&U&^p z^JZ0Jwkabz7&ibw;rC~s1k+;%0GK5G-*eUeYlBYwR?4y{?b$zw)BBYz47})2_D)?u zs@j`>5D%ZNg8saCEUeX5yx$?a)kYzdylG>mhzh1mzQ*pPUa`=?j5=-kxb{8zerDTP z+@_g2Y(M5(erqoBeu4g^Pi6AxvD>HQg6>JSvHo!bqIGJE-C29FoSoFv&oyY`1vU%{ zkr8bg#ZtP#k*%P#xvx%J5^d>q#OYVV2MM&e=N5Y!MVHO<{Hj7@+L%!l4`vS?i7JPP z!(!Dt^SeJ@4!zXuCmA6}p{BGdO} #@YmTk@$6d%r0+CN!3safxocB!!0`Uw^sl=Q^B(}t52(5{`BKIw{ zObm)-^9`oYX-iBi=G%c&_1`0JhKh?9VAO}p4f}1JeKcK8Teq Z;P(4)A(07F-kvUVY=)pMxFrU&Nrt7iU8h&Sj~1=A`&hUCHG3r*l ns@+qA#_KO)mTdN@udsn@Y|j$pt|k z^toH0S>vT~JTqSuvWD$`oujYi*@_#lA6n|9k>sdTCuzux>sM|p@-M!-WMPReYo9Kr zcK12mG*l^P)&p8vV)qCE^)@| 9r;)zZN>-M;^ z%0GI{tXc=>{`oC{SlUURZ?ojdzLc?H#AHp~*Jt{+$G%>vsxa)hv6|jSDcsR=FpJLRgHoV^wO9?MPRo$N?0MgS}Zr&?q(QUmo-!RD` z+nzK~{(M~ql?##S;<@Bs0A|C?_DJoa5DPAbDFr^3(GcZS2U2{jcv0zq);i=Y`I&Eh zg_;?B%@I=sk8hDfLPru ?ZCC4_M;(2I~Kc^FZr3@{6ri ;R8ci4*>0IVY4B$Y=Ka2yx$1X^^}b=7m)~@1GH2C$uhEat-9L?c91G=o4?Va^<3n z+3p=3yOBYHWG{>bBv>=d^pm}XVJE@pKq5yjw%ekQ2)^|nhBh1{yJn6@9BP_&Eo^5V zJ4W^ki3}}%$lh(@?3wHP?5j-hHW`F=2f))g$3NlWIALk}LUfGx2={^;cf(qb7PBi2 zZI^3IuE(V03}WMD_apE;$0DNM$-J?Z-%BX7(gu;v60a+ `wJUciGGMS3ap4c=dae-=!>$ouBA;v-Mq !6>mk0R zGgfm$r55@;W@H~#I?v{Mn9}#+FT3x^1*g YdGO|EAGXUMuoRbFbd7O72qoy|#kgUkID5FAiqX zx>u{_A0s&IV}NT;8I={aK?lfXi}yWqa|!39+6wM}-ly=K(y-`oSFRrf8(Q4WtANNJ z=knh>slCqwRbIFZO@G#xeH&b 6q0OrSE+G{ry6Zn}~0~j_qjeAJk9)n0r&wNWunxzt5NCn!Ag;JN?6bo-c?&c@RQ` zlM?hSlL1g(mIN3~P~DMkZ2{PnPSBA5a|gY<07|0r-aT|yF)Lf^yor#u1x?$^!)I$E z$Bs|qi!UQT>-VXU^6gt~hqSUeFR0J`>fB1kPzZKa |vJiWRi#dw*9F zCAZS(kx}Rv_r1?`m-PkY^B&9LIikZg6b3FqxgqiL@d1MkFAT7Txbn>PjS(}(l&v+X zp6tK#={ehfZmgm7=7Zm?xl!7SWR{{wrisi7(LPC$2M0a5^pyWGMdh_wOwqH$J(Y_D z>w2p^1%LrTYd;v%`JXIL5sMe=LcqWjecL?|(=sj3O$8sqIW4*&NLpN6a-8~*%Qc(r zU^`Q3{`PO{(~7=2xE1TeiS^l-)#^MwZe}5`( ;^F+e=Zm!; z#_G$s!S96{8$-!K3f7$dU4KK${X3XMM$eNPHWx>xOTRcc>xR#wTql(A&X-SN$zO%% zPj*pK>8ZB5ie=Kq@~muCRsr*3;4$x4<*sG_-i~sfH&MkQ +Vjov*p$031uVLQ_c{n{D2gncQaKk39f=$pF`0V^yi!m#;VIIX#!G83 zhpyD~l0&{W+h|P8a^2c-rbsR%8wjOHt_!yC?3T-;R_CGclM&3#0w30pN3j~1AQJn= zvCWw#l;Dh9-MZ+1FlTGd3j1D9gEg$$=l*!)iR{Z#tYa(-z6gIG=r3M_+2Imc7w=G9 zGXlwFw-T51+Hj_b=|7M T)GW?zdU?MI?_3q2Wz+9LgOu`;3Xcz-U&@R zTVKnXlo$%bbja>WF*{F##{xXW#z~s7s(r+Aam3mnwIl|4EA35!zwMq=t#t!+^`MMh zC9h&()4TnmO8vKDbH73VBG?S3W#PIP*?2~fQst0AirY fy z`GafpS{qnD-v(;amU |U3P6)t(5Axo}KiX9fq|2#hhT57|#PI7sq^Qk)%iO7{_1f%vB!%8?8S0J`M08VG z3jAnMB)WKL_p6FLC#=WPQAj-s*eueUTFD68eG9QkchNrc;9^j&&r?OSTy078R}eI( ztW6j8X;s6c_{7rTotLW`MQ?R->KZXGsMQqB4ZL%< |E;wK8S!9;`?Y&>YIk0xOdKC4z% MPkRkN*6gI@ z4kzQ44Cl}vpbXwLY;VbpkvO^0SnX%fq_u%f;ulAYayy+ahl(6|+q(rX3oSXpBA5B! z9v#0iyso!%e{H^=yc>VjBGzRzc}Gk8*f!HQRaQ_abB)NjPs-j=`Z~#CvKrLp5qPJq zxzajA%Nkr^m=gY<2nQ)U;#Ev)l9L}@sO&T;(1(FM4mI(Q{W#TkFmk=;KKxd*S2#sZ z&IgEYy9?rBg>b n*6ijif(2qkY#mXyvC<6VeRE(`U) zBu3F~0%93UAAJ%^vuwSnw|f|BXTPR2{^PG*_tMUIqy9vhC3SZL@28kFDMB8wm$s;e z?wL9kv*Se!%GFy+1N49`D4Ch_ >0Tm$QMT;%QnNyrQQX**86j#bsX#TRF`o>HARc6EIH z4QI ZMo~J`$?BmbIoM+o}3Pm@^oxPRaQNW=i?5B^0Qc6WV6#EcM)|Z&M=)572Z8ENEm`Yv&DcU?bb_n^s+v;98(Wj;cBMB>5(fQOW@kGS+ zKD!de_VeEwRriBssBkfa<9=gEqP41!s04Iuh#pk>vkyuc398O3Rz%%Z`O_;|UgVMq zKf#cv)U^Uiq>%ikRzz{+{!~e^W%UJsIc{ gCYHObtXr+HyO_qd~3?fLp4m!B2cX?h*IU%z8%mqfTH$3?JC zEtviB`9UR8-Ew&f7iy~MBpoDw%_BQem1}BP$(r=d498juUa}hP$Xz)G$yAMia=h?7 z_{t9I`S;}3dbYbp^`l<8{l?rB !xY`f6(wysp fE3`#FOV;;9o6u-^oBdb}Q3j>?UUGV1{_I_JC zo5bd`wXmhub)JdTfFVH_`}H?L@%F~S=v-xTi{vRw5Z4PfqFk@b3h?z_iu+xTcOpL; zy)$bRkZmBXJj^9h pw39_OT?sX% zBt~8Vvt|{JqStv6VbP@yBlse}X~oy142uD%;ptkPjWrMPe6d2%H}Po j ==Z1jdw*|u0gZxi;1OtdWdWf|F_ zge4F6d@Pin@A*G0NeS-T?a$L71HWCwJzd}pKwao!v&q0wMpSD1dunyc07;iCh-`3S zB^ARvJX_}4uVg3K7~x0c1bA=|)DJ)@Z*bPI%J1~S;Z<@`znog^ND?NMewPuEEZ6IR zE#`>7req?%kmF-bW@|!4%=+BR)W3Y^g|Hm*D0FWY!s!z38%VSQazFQ66s8ARV+Dj5 zA9J}AUXJ~;F%3>1vJF9*x7EjWwH?{+BByupbo%0YEV|RC-v{0WgrXFQU)0i-cRN81 zQqpw7U$Q}}zA>1tk(p}+!=Mh)^^DfC{IE^VuNr=pFKyylw^G|x_{TL9H%n!i2>8!p z+SYK1tByLe+h4=spoV8Z1vwL^HSTbCrpPXWx7C`Rq8S$^Cr7gZ2(6l6yPT=)tAr+y z=S|k7Q&YYFKBskZHDr*-=uVB&&Sh1 _*V~o}5QBEJsP#WBY5(2Q_g}7? zB*r3%O7CK8E_?*Ill^U@=s?OxB;ScdY0w!neyOe}um8hbp-Pp8H6PiVNOAxX&&^Tr zvGYH3M&WOqSzf{wk`->FW==1urk_ZF9;BBrlBHAEU}$3iFl*{_ptvSsD+YkbKuSvL z2CVdTaOW}5e>?{haI%u?aa_Pl61x1c00Y40eNnSA eK a&q&^`L3Nadz<-2A0Wy*b5>;YG{{IJe7-kLt diff --git a/docs/images/custom-api-preview-1.png b/docs/images/custom-api-preview-1.png new file mode 100644 index 0000000000000000000000000000000000000000..4cf4c30f1329a9366a2e061cfc4c4ffc7437355b GIT binary patch literal 8068 zcmcI}Wl)^Ww(bBS2_D=-f(CcD5FiA1mjQwgFu@%X++7l62oM+`NYKG8xVyvPu0wDb z4*B-pf6k9nx9+*OtNQJySFe_LwbbgTBh*yna4;z_0RRAw{0A8g002en5tlwkef*kI zya; l$v<+tNBlSBB>@0Ck4pbZ|68Yk$D;UW zfG3ZdTs*v7DBu6p>favGzyGVH l0iw)ei8q?mm`C%@(BS_I0@sGAYtm8sIz9(ms!F| zgWrVv1h)r+ed+S@cpq&siWhW819;2(;tnuM^h6TChu)3{P?kDDd#m~XMa0kJb<4!L zyk`AQ`W55AmfmEz@&$TX(AFV39er+rVD+G8nvI-Q0*SxFuz^+7l=^jH=UkM`A`c zG3sLW8JhFd#K+Khtfr1verhANv8kHT=(OIUN3+)!5Q?R#ub+}h_1+uTWPKo(I-)T> zJzZ pRBw%c3Kn_LaTpAjSP_j3bhj@as8>sLVetEYr zh)rq=40KiIlLXAjC!CNEPj;tGg#8eAOQ?|g0V?Yu=;h0qkL>x^b9mz#NeV=V_Ih#Q zLn;bGe)HY?!hcY>#NOM_!n;5v<>g&8s)U?dd@L$l+_a>oHw8BeDZ7HK+=R8i |4sDaHw^=?A}e^VM&${%D5s5Kulb* z+HOWW6|A2)`zz8_gjzw~R?pR(4~eZt0mxM7{D()h__EClI(&2(DWt2|u=$D=vc<{@ z)jROeEMC*XA=xJR*4wWbZyGTg8n~V&MKDfj>FbeZ=Sm;0NtE%s|FNW;l3 zb7jdOteRc3N2#A^`NYJKRao1N)z{+>|5)$S&+2BKfxw~Nb+`T662r^&G^|XrxDgX6 zDB}4 SbdZ>_NGtq_$pPbqhep1 (QYiR+-4@=>n3ASaW iV(%eQL_1@%?{KyBa0}*VpTr%X;Fug*53BK7f-p$|T=Ox1gae$+ z-AiNdT?K@H+KNH6A-=%}rr^|Gib`OtKl1mYxf`V%wR0_JXf!tC3&@V3K#e(1$Hc=- z@1$BI|1GL8ZFryEB!A731Z#pWQC9VicZpHWAf@pMn&~9j?n)1Y!8-L yayPjg5(n@S$ zMjohU_=NPXt&nG}T{U`xTXEaAc*i_D!e36iVy8h;2dFpx!^~oO8-dK*XwvCcTqqUs zLPnPBmRxnhE9saVAKX^=ugSMn8EVN!fDLQ=txjwPJh5F%pw}c#@7~)>=Qkh%kIIP< z*{R%r21iMg?@FqmWz)qzoE?Jpt888451Cg{tiHH_yw2Xc5E_7KXN>O%9)Jx0e|0=h zvR=uTmy}Q?^;vM4c#Km40JJYooU*d0H}2HrDes(}F+Ep2+!3cZv{3*+IpOkHe?QN) zuaumes6HRP2F`7SM0Wf7=_>>ZnSf{As#I9m%a@-m#^OH^-(A_z9G~@(1KPMcr19|H zI$M4Cf$8sih2kdxphLwIXXdPKpYjLTU
|!yIAF03g?R) zxZi H?rni1tR`G^+^C;$u(kO*_SYa;V zVbO;X`QF#rUGt|_(T5&_LtB4Gk*NsM2~Z!ZZPR(X;7en{2Xglvp5^F>qWmFtRA&tI zikiH4mX3?c9KxLF)hz8bF|9Iruo?{?tGDr0{r6XcjLxU5Q^{`YMh7AEj*^Xcp@}Ie zDU4q(Km56)oz7{TS=j!wTcjpgySSuh3~2{*G`QTsf=*?!SBWTUz3;M;s3Bm{LLN_k zFQ?Uq7QI=8ra;uOlqKQCy$07r#;Pjj2Sn_l99CZ_&&i$n(3-qRq*D99PfQb FsBmFdup@6n2l`0qQk|ifrs6Fydnz_aS0d<>h3U710q?7(@iEmv2$6wIBNMC z#DYKVAAMXus-qpMn{<|avIJE-^v}pm)x!YJvLDZmmnMoD<&z(m>Ti9a$ge7TbA6d6 zs?mDRt@!IpOa}d=N=>^^eNj{k)_HEBakNCxb1i1~=&xOZQ^#``{Ld!TguM+e0l}87 zHou)Y>6&o)^xo7pDE_fJ_kB5vdemjSuolc7XQC3zxkn(gPj90Nyq>$|uzAx7_DOYO zu^*9Ly~v#hsaSs ISH6wj$sLlJu8P y!TI${#}1B8fWr>W9r=3 z1LANv^&?TG@?v;UdUfnnl|Rc5?wmXnJyO)e@)F+aBMSMswNa8ud|e*SE4a1}rr(}{ zCCV{WxZbr~3#icvdT%e!24iYlw_dA6cIvD?>-@!;7A$15E()Tdq6&O@)KK5NP=$w4 zqv^mke;IS8O@nM<;<<2Efle$kIL?#LOi=dnM^5;>$gv~3=b=@ t#v(IB36LH#$(hWFnufwmnKMA=~YC*F`vN5d2exG-ki;UUEJ%~{T)wo}} zO_Vo$f@)nASIGB60+NkSTs)jstg|FO6@8C3OeH4FnEwH`lIG}uAKeCYTR9D2ava8S zT9Bm+$9EB|l!y1d`zhkfp9WQJ=@|RC7o51ix_zphV##ozx>AW P+ZO+1v?V$d%)iC;Y}eWROL`^k1=|_tAI4P6EO^7(@1dUJ2y{I; zWrm9TAwTcz&~?MqfV%4^6~!fAH=x*lnxfA5p?#zb!Auqy9zP(K_M)G~y@FyYSJG0< z3WWkV?iOXbO5C-X1~8OI`UuByk$|%hL2*+5V6Kva93NMD)`2#qzyN$5{F+M##mY?j zm8A9S*hr?iE;kuv13MP+O}*>--owT+d{AnNr8y%?Ydj@Y{Yk!?+stx*+Fo*UduLeF zQjH+&w6|!wTVV{^T7}^^eJW=;G%AXEN*O& la{8U%d02doK?+ZSwutUJ4>L$2~$yuoT_8swxk> z1=e!!BWsc>p26;k+*;vDxZ(~t@6FcC_-f^jKd_3oJ|+9API8CQhqu7)n|f TRzuyNUtEC2D4mUr2XM%(2%1(>#Z%Kic1vor> zam07rZnst7MRO;^MxGaM%r6S_;KAk;^)hZt_3)@KC<`6;6F3i7IdHevDLBesD 7OsVfWE9J;@isSX`BtBM`q!1>GRIF*oxh9tQS$eDonEjO3 zVMku{ePB%nti&K(0`Ds0Jhg@~j!7&aNt2hMHoKHIs_%`B+p(hMkjs~E`_Bq7Yd@|C zN;H>keU^AXH|39VDOE9^3=7;szwuO^0m(-#o!u^3xt_e&y-lgFi0DwKTHu{U@p*Ht zXzR*dPj?!)*2J0iL`iVR*VP@K(77!mIU1ieVY<=p D z 3u6)v5vF*4QHz?^SfyPSl1^6(Te-vUGY3C z`J!b_*~r?x&3TPL7H(ThI{8NF9P|0tb@7FP0eN9L1Syg| $KDqm5PZ zwDtAFO#$_D{j~%%>w!_5c0@Bf A}|e@xJK7ltz5~ zyy*xDKklXn&c|soB;?`z9UQGSS5hC%R4WnTgB af*!MYZ5g cPG-J|!Sz8}>0&BTu5;m$BO^LQJmq(!Uv zBlq!0EXd8z OHZW0E_dVb04bEmGhnE@#mEJRbKXc`NM9} zO7|(JAuo`3h8&)Lo?M(aXF$hXpkLHTwqjOf8cP(bi9}dJ4=+q>C`!~|lS0JsC!_yJ z!OpFXgBH2{y@2fXRMsFD&c$TX@!qm&GHAAWBn#taq)_!+dn&=rW^NsJZ6_y17j&%) zyCBT}0?9_G&1fPgkDw7Jx9_SIn{O8$q=H1muv|`#vBat29i|(K3LFkFPQM>R5MWCm z27%uP&Kiw(u8Jb72dlk0M)qhHE*6O#xfH<{q(IIC!^R(RqaZHEs>^gXJy=JChYN7F zecw$7xxB^FM6k;Fb1JCy8j_dbVsG796b#)P&V0-CZ2^WbeA1;rLM8Y+H8{g-=M&p@ z)fM<+1T14Dy*poo*w!dm%O6~eOjAviN4f#OsGEM4Jp$v$VK?2+4q1bV6?#nvF0gC) zb?ut!z{f?mr8?m2;mMyOX&Un<^k-6QILUg`#Yh4LQ_1+~n`CnPB6Z7OvXVNa8Ih!x z97wCw!DjgH%bsQCDR&Ia^jSAv2^ug_WU8E~P=wR=4BGYkOw*{lC48@&<>jp*=rNIk zjhDi2_1l#U{J2>f2}~zmGc&f2f@TC8reQj?G${QbQ#PQ>Y1^0CPAG*65}AurYjV17 zjjNn?v07sxpzq0kBJk#BB!~rrCTGT+&Fa{4uHtcrWyaKpjgN&sd>i9!afaA11Ib!x zERWeg%({r=O$|DdRIDJHjUas%Kw26iP--*tg%BNN78G&q(p9h~TUc2qpu0svw4oy) zm||s}^FYqi>Gz4=>Q@S9%ga~+Ayxs78i=LcK40f#`hN`2S+F+s&0aL;_4$TW^|3z2 zDihLsvdrc^TaLY#S)RqFPK(W(Ax4U@c6tg~=Yc3*wi>(^axft|CY>gQ_h#Hd3iKBr z!~44STf(~N)6h=qaPcLBpAvKeBvXlQ5_jGe#ZyFxK-Mlf8$ODJ71$VM*y((FUp>UN z`YJ~$^vmgW?wj3a`co5$k=|)E+1AFSnuB#d#Dx;U+4co}^I=LPDY*rSZUnh~24%1{ zfUKMJLlS-}Ptf6LxN;Y$Fh9}_qakB;xbN^mh*?QpVF{r{4{H+ot?@W56(POmCNmsu z4fA`!a(l~6cc|*{d3E)8V-0D0iQ?v;KBI<9A_APgF EruBe 2O8QyPvY6e_YNx_>1Oo3a;3 zXrAe~kAg8(V7eT|M};Q@K<7%{^6EGZQ>!1~@dq5OU~>mKIILqS^;l3OSWLfFjA6@v z_jlK8KQ*+Q+KpqGgt8-_Gr-(jf%P`ArSCFM%#%A)NkJ# l!?W)aK(tZO @{YA2(cGyPO#OO>7k;}P&2?bT(|b7URQlDvNf!UW@`F3? zO>sFJySHw@Wj3vtkQd{5V;3t-Nsjk^IY^9-2QePH`2_?EUXj}vF39aH{OX?=m)=_C z-Q2j-+lR}rSEM@Iu=o9!Oy(M)=mm4Y1rk2pNC2#5IEoTtYC42${OjMS{w~`vS}?rU z=A8e^M{yG3;(XbT?c7Jk6Bw}ZTVrA(&0%AjycF9I3>m+tmH?QVcH2;J5?vQ7Md$DC z9DRgN=_Ni(z-v39D1x+ZgIBJUyL2z^^B#PJQ2{0b0uN23fLHvz%UA$1%>N@sq$mN) ze?P@cy;1shL;r0ET?)Ujr}#G#Mn)F 2M`C%@OA<_^MybAvnYb`&JTjJZ z@RHI*cKs-O1spp>3pbj~9Ymd`0UL^zUUbG8a^|^C&QIw2U$jIO6|;5!`ySqfbjOeW z#r?IRaqaZJ5w>1$r!w5HpYRYVKpk6D} zo=tMQZT+BNsFLuOLKE2JU7GQ3evBIb@gkNbRE49p_vrGBjbU%*c8A;67v+FR(n+$H zDg0WgfuCD9eDJzs!VkkZJFOAaLTA>@33Dy&h5S!7Jzy{TPWI*-xTHiAgopzs&n*;* zGh7VJ5%v{@nnKnGhS#g Zh1ZCUe*5rDXA&Q0AE$+oeld3AAIXOrMj!>tO%RVvr z5D^DqZB*N5ylC$|4ijLI@0Dp42M-rt8l8v7vMgArOIEK^H)$Ltr1*4oln|PsEk#+M zFg!J5I$ZoKgrN+KBP3BGAyt`vI|W%`z1lgV%UqVXeO3bhm?G)hMTXk@2P@af-!v&P z_ZvL%$+brIsJ50~*N}N1LArKtGcBzRJKdB;-d2VSSIVal;6e1P>d`s@sCs0B;3Skn z8hm1!WUZP12}0h`VF=sW kszBLbtlvC&`gT2^?k0^y gEnc R&y{meQZXdl1tPE#+SmTObrsnNPvN z30TPfP(~&Fk e*Aiz|;qE%@ZG11}U1_AH`Pf7$Sf)`??@uKeoT+ut?>#f3h< zp8{`JT+|gACH`7{H!Q?5@MvDw^DE)VQQp-ojR#QgDTfP#K}+RUecRwUTCx@;a7s|Z z&m^~Hpd3{Vnx|4*yg2TllxF<7@Wk*!tjs9ft6mqz^`6E+$v5?UCP A0?*Jvtdnzh$Y`RM`ACkdlSkpcdWwGT$^m!S@6&UHGfcCz!DplGl*d)S zg0D(usc$K2{rFH=zxm`y6NhrhZq?ykhyuvMetB&$d;M^#*(|8MS^UAIA~XuzW)vIO zBNH?K f9HVgjCL2nHH<)D2fX!2v90kB2I{+s~ltwUvsSB`gVw$IQJ2*l_E z8khaar{6)ic;aG!zTDRdEMKg3Nfn4$nV@YJJg<=`WG^2%Y^G>m@^3kpa1C@x%!e`# zX956MlZA!FNkH$n_9TQ|tCkxY;KwV6Kl0>vJG0VM{s6%5?Uc@} OQ2+n{ literal 0 HcmV?d00001 diff --git a/docs/images/custom-api-preview-2.png b/docs/images/custom-api-preview-2.png new file mode 100644 index 0000000000000000000000000000000000000000..481ef8536817027f9b92496a2c82246b12be53d4 GIT binary patch literal 5826 zcmcIoXH-+svOb6?AYBjv0a2t#2kG5VM0%5wgd);=@1RH#5R@*xgY+i7cd0_?gd%DP zU4f8L0(tS?`~JN3*8TC`y0g}tnc3%?*=?OYXHT?_mMS?ZBPjp? QkV4^4>PyxNfVcsR#gdA8uhSiSRaw+cOhS0HEmq%LK!&pI_k{ z?|La4d+EE{c==j-SOYqi_AXxhTFM6ZMfrvJg)ce?oA8(>YhyJVHMPe8G2S2o7zu~~ z0=)Jd&rJW)@uLB_2nhet{&ze=1lIs6yfnqLebn`Tv^(JSzhr^uzyAL%|3{|)Apm^5 z30%h`1cgNe3G)6K^{)p}-ajKH 0PZV1!7o?=0YFSe4k)~~!_QlZ z5TN=GK&E19`Ws0C9qYQe;TE*G^J!dt^5v~gq9bf@E)JqZo>}K)|E`wJ%6v~ZTJsmv zt;@5ciktHC>;=4>0vGCewO2=7&LcGEq6x0N6k?X8{ZyCdF85^lVty>jGM%h6_>@4P z%IcciBjNq_&9oZb>wTD^xxM$A{8o(PW3n+_`dZJ)e Z$e2!)3hf3P^wOhZVk&jU?#fkaEX5AJWT7IX#nxIz0 z&cTip79qGxbq@rxLT@C^u#b$5$eG&+jwa;>`hB|+NvnQl`U^E`wI|%W-cp5NU>=FM z*7@3`i@Et1wgh{NNZ1OafU`aLLhStr8FMnEeX{>K@i_DN8{JHWmcGB@ uRfY*8} V2MPB;3)$^VXmj+Qw_J}V1qxx*|qQOqX`hLr>`_xvoO zlctSHU0z<^x#2H8H@&O_hJtyL8XnRbW|}KWwh~WttfFFF8ky=kzho3V7+o9G*xDcA zDQ^+avnwwxotj!!Y#d|SQkzaPM1v(wx6{mJ5+9eS4swsA(?C5rJrQ5uiinHC_|)ay zG) Aldq8 zAwBoG*!JbmjRnc1hCs?o-GTrzK_Dlr|6@VN0}#$4Dba} &qxpRIFu4lT4F2b9_{+VX(cfvwnzuL|GM2?*0Mv zcq#lgB6VgxWY^WP0I76tg0bZQ7>{X{2n~a-f @AH?n(ZRR<=nA&6 zW#)#`&@=@|e#19KX zvQMQC7@tJgPPH<-irOP~w(KeW@4|viQ9Iolt${6hb;?@X9<#1Q#LT>BiN}G-OdRcU zmsJ|yCW}8f3FfxEJc0e;7qKt)^1i4mBgkVgr6#{en6G2!GB8u@g^CN`e42mQ|J&H} zItPmOJ<6L4nnNwi9Z)}dMXIY@0qr?vqd Gw897() zKKkePgI!aNYTqgaQKng*SV!p1NyhGk9f5 lq 3OJ;w(IGkOro zqnYR(+Y-J!)k2QD$*dQLX*o9q&dc^@DWgceRVE-B+M#NBZ?=AQwLs8}91r573N^tI zTL=8Q&T8r7vmxQ @HO5pYB2I%+$Fd E!1#r4vT8OovWjx zb^8;=Bx%~weIjTpBpw3X6-4c*)OexFRcl^5rE%B^Gj3fH2L!%x26})3BiR6=S4 PPLuDAEl{^92?3%8)QWPF8|>1cCN0rtOPy!S`E{$ce8;TBzrplTMol_=Qbn$ zS`mbYIaA@YUlJzr*D*O53|<_1`z~JcvRwSa7_lRsWc1sb6{GdN8+GYxhN_!Fa+&hf z?BOhCn$tCdDa%f)myXrgy}kCwav_$1k;#E4tusN#J0Dn2K2ts-Uaxm84BbGV?NWL( zP={Ba{m7P#zqYfppnrZS@Z@e8H k( zc5_pu>F}#WWaQ9Zzv>X;h&D#r>8Ij5&q-WPkj5j>2HlV4jLVrf4TwEE*GPe7^tNzw z+w7@8w m zRxme5$7L@M3+ycpy9Hr}gLLC{S${*sy^Z6FmKR%uJbm@V;PT0zxwA9adT+4~bjh{x zdE$`m2j=%x<(p@5KG!T;LuiOR5Vz_5Q1Shxu)RRq%@oZ9Kijq|C=aU&DVu=%#Ds ztKQd+u6J&%BNy}6NcuR>cIa6GY>$nGL)Fg%jwAac&gGJ9NY3x-9YQ7Lb?!?xmhK`q zs9wt2X4G8GvA!tVY1p`AkM0Q_h4|=<9L5=yeoA4!bc%YnZ=qCk5i6f^hA6il=2^_i zSJm8}H53gB`=F5c#hS2Pf#VK|N?dL^ BaI;(E;~ka;uA6E
!ei+U!qHx(F_rFBt)}9seCl MPXQ;RR`Oi{tR+P4>upqQ&~=b1q8U7hTcP z@Uv;}v@%SGrpW3JES}j$I)`gNI#R`b4Sx(V?QwRaH!yJe6Wrof!9J&+mW%m7QyUvO zNx^26sSf##pYn3<=L3hJb}?nC`iG!oD^yIGn792fWxaFm0#0V~^WN!X=XfF$bCQP? zhp8xlY47%eer9;^$1F9`L+TO2Z9GP|pvDMyOkYK8u^)Yd!)u|^R2bQ~>VI!tQvKS} zf!w2xZjU)8FwNo%@o=_X`KY*gquEsU!AfZ7Q757Grv7{|*2ONZp9&Ov-)kmHy#uc2 z8|0-oXUW|8vLtw-j5(KL5cHn1NOk*QJJ_zTgms%(=L*|mF9TQ8B|5BlQ3YvqxQyyv zJ2Ing4^9w; u#iS9R!hBTT3T8qs!DxKY@)E$4&aC3|MXB*|*JIL%gNL#WBq_ zYgnVifd{X&B&4MVBve9MgvMKBEa4Zv80NmPj+5h%tD@h9J)nE}UfHu`x+dn%1rIF{ zoMoa;Q87D$uUv)>ogICOxPxr?j$Yl&VRwFaBiE#cKX46q!09^!$_Dm1<0+!b%Q`R# ze#P~XFmb_`U=Ydibdy&R@7a2Voa9U}H5zgxaxs!xUwMJx$eRt^o+TH`cubm3)-tyO z*Zh#7g-Fv!^J6GT $V=W(PmdurUxH_!&1ij!ba9nlohIX7y?Pt>TiJ)`&~|i@rM#-|mBzsPkB1LW`IujP>#9db2%Y=iY-YCP zf2b>Bp!ZTr$YCC(<74*|Hf0Gbat6;t&ZnOrGIc|w6_I^L;LvK(1|8}h(YYsIbosmu zq5hEq%pmKKinf*!+xhyhYF60GVL!jPCS @ywVczJ|;XnQ Le+RgZO&_F*b=01mX37~gMb*d;_;A^OPn^SA)n&e9Icl3N zHTuRgQwAQv8P^sMvqf%wO13sYD({9H=^Aog33VgKZV2H&Q}CQwTANEvo4&x6)o Iz;7id z#_sO6U2#o|`z0Ct`s?9??M3`OPL6z#nH0Ed@$a*{LMFd|eYEjmL2ig6xSe0M`Rsh8 z< %88{p?OOFA~2J &c%gr*c`nZ zJi`=TcE0x;os)p_W0a+i-ybmAJO#UPm793+9z1K(kVGnu+ni@0y(xw`V$&m$v7t;x ztw^~3%G5$(Py{5HWo{nkbMX?pmXzY 6(&Sgj-JCw(@X^|Q{gR)LA6+j`Tt{jJ&4%$!n2L(Z_ohuw}CXQ~iNqOnEU9<>ar zi~TZGL+i@Nh@WKj)yd??8BS)N=NZW?O(+yzS2xV1e`MX0XfL!Q!l{+H__co-X4c zP*!$ELc-(b%*wP@1bkrDNeFtFqg_!NuD==K9s)nJhP95Z)TtAC>DQ=98;G!0zG4>Z zl?&T7dE{jSKh^ZDmQON;taEjJO3-!q^;0jsmXE(tsrAWHfaZ6b5cFWem*co<-6Xyv z5oOKf6T95V@WmGPwk8G!`oZyI9mCN@|14?mxU)g-+sN0t28yP2@A+ff{V<`F*c?-9 zdDoJ+^}J*?-|ac7MDGO5A!Abfw vg;VUvv;n< 0e&1J(9=Uir| ?Ml5Z12z2Romq%o ztmf1jE9iZ-r|$LUs>{8pYRm5j>$nTAa