From 87984e2081de4e436adac552f520c02e07e371ab Mon Sep 17 00:00:00 2001 From: sharevb Date: Sun, 25 Aug 2024 22:57:07 +0200 Subject: [PATCH 1/5] feat(new tool): Markdown to HTML (#916) * feat(new tool): Markdown to HTML Fix partially #538 * feat: add print button * Update src/tools/markdown-to-html/index.ts * Update src/tools/markdown-to-html/markdown-to-html.vue --------- Co-authored-by: Corentin THOMASSET --- components.d.ts | 2 + package.json | 2 + pnpm-lock.yaml | 61 ++++++++++++++++--- src/components/TextareaCopyable.vue | 2 + src/tools/index.ts | 2 + src/tools/markdown-to-html/index.ts | 12 ++++ .../markdown-to-html/markdown-to-html.vue | 44 +++++++++++++ 7 files changed, 115 insertions(+), 10 deletions(-) create mode 100644 src/tools/markdown-to-html/index.ts create mode 100644 src/tools/markdown-to-html/markdown-to-html.vue diff --git a/components.d.ts b/components.d.ts index 89f41f80..8e59366a 100644 --- a/components.d.ts +++ b/components.d.ts @@ -121,6 +121,7 @@ declare module '@vue/runtime-core' { LoremIpsumGenerator: typeof import('./src/tools/lorem-ipsum-generator/lorem-ipsum-generator.vue')['default'] MacAddressGenerator: typeof import('./src/tools/mac-address-generator/mac-address-generator.vue')['default'] MacAddressLookup: typeof import('./src/tools/mac-address-lookup/mac-address-lookup.vue')['default'] + MarkdownToHtml: typeof import('./src/tools/markdown-to-html/markdown-to-html.vue')['default'] MathEvaluator: typeof import('./src/tools/math-evaluator/math-evaluator.vue')['default'] MenuBar: typeof import('./src/tools/html-wysiwyg-editor/editor/menu-bar.vue')['default'] MenuBarItem: typeof import('./src/tools/html-wysiwyg-editor/editor/menu-bar-item.vue')['default'] @@ -129,6 +130,7 @@ declare module '@vue/runtime-core' { MetaTagGenerator: typeof import('./src/tools/meta-tag-generator/meta-tag-generator.vue')['default'] MimeTypes: typeof import('./src/tools/mime-types/mime-types.vue')['default'] NavbarButtons: typeof import('./src/components/NavbarButtons.vue')['default'] + NButton: typeof import('naive-ui')['NButton'] NCode: typeof import('naive-ui')['NCode'] NCollapseTransition: typeof import('naive-ui')['NCollapseTransition'] NConfigProvider: typeof import('naive-ui')['NConfigProvider'] diff --git a/package.json b/package.json index 6191f702..63e5856a 100644 --- a/package.json +++ b/package.json @@ -41,6 +41,7 @@ "@tiptap/pm": "2.1.6", "@tiptap/starter-kit": "2.1.6", "@tiptap/vue-3": "2.0.3", + "@types/markdown-it": "^13.0.7", "@types/figlet": "^1.5.8", "@vicons/material": "^0.12.0", "@vicons/tabler": "^0.12.0", @@ -70,6 +71,7 @@ "jwt-decode": "^3.1.2", "libphonenumber-js": "^1.10.28", "lodash": "^4.17.21", + "markdown-it": "^14.0.0", "marked": "^10.0.0", "mathjs": "^11.9.1", "mime-types": "^2.1.35", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 3044541a..2311f3af 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -26,6 +26,9 @@ dependencies: '@types/figlet': specifier: ^1.5.8 version: 1.5.8 + '@types/markdown-it': + specifier: ^13.0.7 + version: 13.0.9 '@vicons/material': specifier: ^0.12.0 version: 0.12.0 @@ -110,6 +113,9 @@ dependencies: lodash: specifier: ^4.17.21 version: 4.17.21 + markdown-it: + specifier: ^14.0.0 + version: 14.1.0 marked: specifier: ^10.0.0 version: 10.0.0 @@ -2952,7 +2958,6 @@ packages: /@types/linkify-it@3.0.2: resolution: {integrity: sha512-HZQYqbiFVWufzCwexrvh694SOim8z2d+xJl5UNamcvQFejLY/2YUtzXHYi3cHdI7PMlS8ejH2slRAOJQ32aNbA==} - dev: true /@types/lodash-es@4.17.10: resolution: {integrity: sha512-YJP+w/2khSBwbUSFdGsSqmDvmnN3cCKoPOL7Zjle6s30ZtemkkqhjVfFqGwPN7ASil5VyjE2GtyU/yqYY6mC0A==} @@ -2974,6 +2979,13 @@ packages: '@types/mdurl': 1.0.2 dev: true + /@types/markdown-it@13.0.9: + resolution: {integrity: sha512-1XPwR0+MgXLWfTn9gCsZ55AHOKW1WN+P9vr0PaQh5aerR9LLQXUbjfEAFhjmEmyoYFWAyuN2Mqkn40MZ4ukjBw==} + dependencies: + '@types/linkify-it': 3.0.2 + '@types/mdurl': 1.0.2 + dev: false + /@types/mdast@3.0.11: resolution: {integrity: sha512-Y/uImid8aAwrEA24/1tcRZwpxX3pIFTSilcNDKSPn+Y2iDywSEachzRuvgAYYLR3wpGXAsMbv5lvKLDZLeYPAw==} dependencies: @@ -2982,7 +2994,6 @@ packages: /@types/mdurl@1.0.2: resolution: {integrity: sha512-eC4U9MlIcu2q0KQmXszyn5Akca/0jrQmwDRgpAMJai7qBWq4amIQhZyNau4VYGtCeALvW1/NtjzJJ567aZxfKA==} - dev: true /@types/mime-types@2.1.1: resolution: {integrity: sha512-vXOTGVSLR2jMw440moWTC7H19iUyLtP3Z1YTj7cSsubOICinjMxFeb/V57v9QdyyPGbbWolUFSSmSiRSn94tFw==} @@ -3360,7 +3371,7 @@ packages: dependencies: '@unhead/dom': 0.5.1 '@unhead/schema': 0.5.1 - '@vueuse/shared': 10.11.1(vue@3.3.4) + '@vueuse/shared': 11.0.3(vue@3.3.4) unhead: 0.5.1 vue: 3.3.4 transitivePeerDependencies: @@ -3993,19 +4004,19 @@ packages: - vue dev: false - /@vueuse/shared@10.11.1(vue@3.3.4): - resolution: {integrity: sha512-LHpC8711VFZlDaYUXEBbFBCQ7GS3dVU9mjOhhMhXP6txTV4EhYQg/KGnQuvt/sPAtoUKq7VVUnL6mVtFoL42sA==} + /@vueuse/shared@10.3.0(vue@3.3.4): + resolution: {integrity: sha512-kGqCTEuFPMK4+fNWy6dUOiYmxGcUbtznMwBZLC1PubidF4VZY05B+Oht7Jh7/6x4VOWGpvu3R37WHi81cKpiqg==} dependencies: - vue-demi: 0.14.10(vue@3.3.4) + vue-demi: 0.14.5(vue@3.3.4) transitivePeerDependencies: - '@vue/composition-api' - vue dev: false - /@vueuse/shared@10.3.0(vue@3.3.4): - resolution: {integrity: sha512-kGqCTEuFPMK4+fNWy6dUOiYmxGcUbtznMwBZLC1PubidF4VZY05B+Oht7Jh7/6x4VOWGpvu3R37WHi81cKpiqg==} + /@vueuse/shared@11.0.3(vue@3.3.4): + resolution: {integrity: sha512-0rY2m6HS5t27n/Vp5cTDsKTlNnimCqsbh/fmT2LgE+aaU42EMfXo8+bNX91W9I7DDmxfuACXMmrd7d79JxkqWA==} dependencies: - vue-demi: 0.14.5(vue@3.3.4) + vue-demi: 0.14.10(vue@3.3.4) transitivePeerDependencies: - '@vue/composition-api' - vue @@ -5016,7 +5027,6 @@ packages: /entities@4.5.0: resolution: {integrity: sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==} engines: {node: '>=0.12'} - dev: true /errno@0.1.8: resolution: {integrity: sha512-dJ6oBr5SQ1VSd9qkk7ByRgb/1SH4JZjCHSW/mr63/QcXO9zLVxvJ6Oy13nio03rxpSnVDDjFor75SjVeZWPW/A==} @@ -6688,6 +6698,12 @@ packages: dependencies: uc.micro: 1.0.6 + /linkify-it@5.0.0: + resolution: {integrity: sha512-5aHCbzQRADcdP+ATqnDuhhJ/MRIqDkZX5pyjFHRRysS8vZ5AbqGEoFIb6pYHPZ+L/OC2Lc+xT8uHVVR5CAK/wQ==} + dependencies: + uc.micro: 2.1.0 + dev: false + /local-pkg@0.4.3: resolution: {integrity: sha512-SFppqq5p42fe2qcZQqqEOiVRXl+WCP1MdT6k7BDEW1j++sp5fIY+/fdRQitvKgB5BrBcmrs5m/L0v2FrU5MY1g==} engines: {node: '>=14'} @@ -6825,6 +6841,18 @@ packages: mdurl: 1.0.1 uc.micro: 1.0.6 + /markdown-it@14.1.0: + resolution: {integrity: sha512-a54IwgWPaeBCAAsv13YgmALOF1elABB08FxO9i+r4VFk5Vl4pKokRPeX8u5TCgSsPi6ec1otfLjdOpVcgbpshg==} + hasBin: true + dependencies: + argparse: 2.0.1 + entities: 4.5.0 + linkify-it: 5.0.0 + mdurl: 2.0.0 + punycode.js: 2.3.1 + uc.micro: 2.1.0 + dev: false + /marked@10.0.0: resolution: {integrity: sha512-YiGcYcWj50YrwBgNzFoYhQ1hT6GmQbFG8SksnYJX1z4BXTHSOrz1GB5/Jm2yQvMg4nN1FHP4M6r03R10KrVUiA==} engines: {node: '>= 18'} @@ -6873,6 +6901,10 @@ packages: /mdurl@1.0.1: resolution: {integrity: sha512-/sKlQJCBYVY9Ers9hqzKou4H6V5UWc/M59TH2dvkt+84itfnq7uFOMLpOiOS4ujvHP4etln18fmIxA5R5fll0g==} + /mdurl@2.0.0: + resolution: {integrity: sha512-Lf+9+2r+Tdp5wXDXC4PcIBjTDtq4UKjCPMQhKIuzpJNW0b96kVqSwW0bT7FhRSfmAiFYgP+SCRvdrDozfh0U5w==} + dev: false + /merge-stream@2.0.0: resolution: {integrity: sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==} dev: true @@ -7682,6 +7714,11 @@ packages: resolution: {integrity: sha512-E/ZsdU4HLs/68gYzgGTkMicWTLPdAftJLfJFlLUAAKZGkStNU72sZjT66SnMDVOfOWY/YAoiD7Jxa9iHvngcag==} dev: true + /punycode.js@2.3.1: + resolution: {integrity: sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA==} + engines: {node: '>=6'} + dev: false + /punycode@2.3.0: resolution: {integrity: sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA==} engines: {node: '>=6'} @@ -8626,6 +8663,10 @@ packages: /uc.micro@1.0.6: resolution: {integrity: sha512-8Y75pvTYkLJW2hWQHXxoqRgV7qb9B+9vFEtidML+7koHUFapnVJAZ6cKs+Qjz5Aw3aZWHMC6u0wJE3At+nSGwA==} + /uc.micro@2.1.0: + resolution: {integrity: sha512-ARDJmphmdvUk6Glw7y9DQ2bFkKBHwQHLi2lsaH6PPmz/Ka9sFOBsBluozhDltWmnv9u/cF6Rt87znRTPV+yp/A==} + dev: false + /ufo@1.1.2: resolution: {integrity: sha512-TrY6DsjTQQgyS3E3dBaOXf0TpPD8u9FVrVYmKVegJuFw51n/YB9XPt+U6ydzFG5ZIN7+DIjPbNmXoBj9esYhgQ==} diff --git a/src/components/TextareaCopyable.vue b/src/components/TextareaCopyable.vue index 8b0aae61..9585177d 100644 --- a/src/components/TextareaCopyable.vue +++ b/src/components/TextareaCopyable.vue @@ -7,6 +7,7 @@ import sqlHljs from 'highlight.js/lib/languages/sql'; import xmlHljs from 'highlight.js/lib/languages/xml'; import yamlHljs from 'highlight.js/lib/languages/yaml'; import iniHljs from 'highlight.js/lib/languages/ini'; +import markdownHljs from 'highlight.js/lib/languages/markdown'; import { useCopy } from '@/composable/copy'; const props = withDefaults( @@ -30,6 +31,7 @@ hljs.registerLanguage('html', xmlHljs); hljs.registerLanguage('xml', xmlHljs); hljs.registerLanguage('yaml', yamlHljs); hljs.registerLanguage('toml', iniHljs); +hljs.registerLanguage('markdown', markdownHljs); const { value, language, followHeightOf, copyPlacement, copyMessage } = toRefs(props); const { height } = followHeightOf.value ? useElementSize(followHeightOf) : { height: ref(null) }; diff --git a/src/tools/index.ts b/src/tools/index.ts index b4c161ef..c9003fe8 100644 --- a/src/tools/index.ts +++ b/src/tools/index.ts @@ -9,6 +9,7 @@ import { tool as textToUnicode } from './text-to-unicode'; import { tool as safelinkDecoder } from './safelink-decoder'; import { tool as xmlToJson } from './xml-to-json'; import { tool as jsonToXml } from './json-to-xml'; +import { tool as markdownToHtml } from './markdown-to-html'; import { tool as pdfSignatureChecker } from './pdf-signature-checker'; import { tool as numeronymGenerator } from './numeronym-generator'; import { tool as macAddressGenerator } from './mac-address-generator'; @@ -112,6 +113,7 @@ export const toolsByCategory: ToolCategory[] = [ tomlToYaml, xmlToJson, jsonToXml, + markdownToHtml, ], }, { diff --git a/src/tools/markdown-to-html/index.ts b/src/tools/markdown-to-html/index.ts new file mode 100644 index 00000000..73a6cfb3 --- /dev/null +++ b/src/tools/markdown-to-html/index.ts @@ -0,0 +1,12 @@ +import { Markdown } from '@vicons/tabler'; +import { defineTool } from '../tool'; + +export const tool = defineTool({ + name: 'Markdown to HTML', + path: '/markdown-to-html', + description: 'Convert Markdown to Html and allow to print (as PDF)', + keywords: ['markdown', 'html', 'converter', 'pdf'], + component: () => import('./markdown-to-html.vue'), + icon: Markdown, + createdAt: new Date('2024-08-25'), +}); diff --git a/src/tools/markdown-to-html/markdown-to-html.vue b/src/tools/markdown-to-html/markdown-to-html.vue new file mode 100644 index 00000000..c84d44ec --- /dev/null +++ b/src/tools/markdown-to-html/markdown-to-html.vue @@ -0,0 +1,44 @@ + + + From 67094980c9687652c10847bf4112ae0f36a31ce9 Mon Sep 17 00:00:00 2001 From: Corentin THOMASSET Date: Fri, 13 Sep 2024 20:56:32 +0200 Subject: [PATCH 2/5] chore(readme): updated logos (#1294) --- .github/logo-dark.png | Bin 0 -> 40398 bytes .github/logo-white.png | Bin 0 -> 39632 bytes .github/logo.png | Bin 8000 -> 0 bytes README.md | 6 +++++- 4 files changed, 5 insertions(+), 1 deletion(-) create mode 100644 .github/logo-dark.png create mode 100644 .github/logo-white.png delete mode 100644 .github/logo.png diff --git a/.github/logo-dark.png b/.github/logo-dark.png new file mode 100644 index 0000000000000000000000000000000000000000..9bee8a9cc024cb685e4159137bfa738b9f68a3a2 GIT binary patch literal 40398 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
2JWcE?hs*UvQR{de2#=l#t>wuk4Y$G+~L zKl}grpNFO9@6Vk)C!VGFfPTmSf7$!L-nXm&8DIbWw$X>x%0W}+)`r!YX}|2;vi|Ra zz3K8w?-RdwPrX%c`OP;f@mlWT_uDc}ei=UBF+Wjuy7TtR8k?t)t?!PWOlI;y0Gnk zw}gLrer`t}_oi#2$MxBI9(xt0)b~#;UShVq@9b8sM3X0r*M+{@_%3-CZFy?u%E z{M+9YUdvbNu`{}L^kLrYT^m;Q&fH$O*mut3y^(X*pLe{s@`vrWFUR)f?vz<;e(!B> z{d0@GbAR1f<9xh#-nBn_*Zq9Hr@k(8-gB-8h7x<82tSL~aX>y>G+Wypjrhm0(e|@6`YYF{C)@l^yE3cfkDBYAEW2CZ z?yXPXe>U2B?f1|1GP4hw%07Q_`%r1m)n5y)C(rT!zU4A6 zHOCG?jID7)<=@RV=c{}E{H744_ODNValad9pD+1Mm-mg}1Jjs3$1SHf z-v9mTziG7j+S)zFZsF4MiqETVZ=YWG>`%W!t)0i^z1$hKp+7JFvENs&H}m76nBMUH z5?SmgIPX7CuifI7eL8Su2+?>ctB+i#Be& ze|ej2dG_QQdHv&;Y`bS}zFK}YYhtL3>AGL`IhFhO>^M5{`UPvFds?SYw5IlNFIRpX z`)~j2Ij76-WSo^WJ@;e#>mBU>S4+oz{IpH(>-XOBpa0ir&szV!zHjdT_41Wc|Ha(* z{eACWpSkY-59|LG>iZR*HN+dlOFw%({r}Vd^?e_;?_cZu|1nqW&+~F=+v?I2?JC!Q z8fyK0q`0q6_Hp4&t2<-P?NT-<{qSb4`!19?BNh(La`5thrA2{qfbk zyUN9Ht`<6a(M&(8Ni^5My?T|^w=3)2x2UUOe zKmY3QM9%Ax&-=9x|6g@_tKh8gX`7eNw48Q7FYZjvxgQ^+o<9rmzV&Vp!(#PS~=bFb~tGl@- z`OEY9e%s5WEqgZIj@q2Mdu`dgpJ~SFNBZ6FDRjR2URf4rl+KuTY^mjUhF^`_;WiUQ4~MUbX%6sjcyj;g(T1uYLS{d&Zd`d$P{W+5a$T zX|3#gx$Vbme{4HDZ`OhS8@nI>ne*K;R&<4-n6>QR9fj+%CjFhhE$->N(7yhUJ_*k& zzuCInI=*7<;<$?)#^w>{7rESZieXKqJ$AIsgi^1{601@}{4I{%xayxrn%IlJ<|Bklpcb;8*xtk3i= z?)0-g?s{}_#qHG>`e*!^!F`Y@ZkO=f*1QRr+#2|Mzih z6fEcc_wmM+)6(1*ukB>q?l1PSew+HG#rKr+3!YrQ^847yyjA^`IaS{-UNke4f4t>; zR{s5ao0HcZ=ba$4S$FoU&Z~jjGtLAazcqJ?fB*W=o}U8$UQ2%0@$TIF<2!csZJnKc zMJlRZcD4I~=OGkSM#nPlaOgZ4^xeK9Q0-(X8&<+u8QNzpb_Z{rsbU{g1=z|DWV%W}p>dqm{v<=29902kLL^XWa4n>i_L? RUp@gD=IQF^vd$@?2>|9GZx^prw85kH?(j9#r85lP9bN@+XWnh?<>gnPbQo;D!zT zO;3&1ZJCfalTp}V>O6+c(a*RmehcrgNq!c*s8y=*$z#DUEmljXWk`fx-81`^+{L7z zr~VJ#>NlK@Z$?1luvwO?zT#i)T3rl%d>^FD%UghHd_21TQj#p9+TN9E0 z@yMyEN(`f5Gz3ONU^E0qLtx-T;K3>rMg|6k4+$ZzoeiSCU9KimpD z-|g5~QE_Ez_m?HFPiZ++Cda>5GWe-x(@|+&`!{cw-hHlhmqOk>Gx{$4GWETiT>c&t z_EYcQyynlhj@y-XEv!c8_6J^m%X{lDncwlacJ=rx=|76s=YHAu(2s#3T~LF4L*!+K z&#Pa~Pyh5IZ#m;r^-p3tFaAd#RIN0N{T|OPCsO)U$#&s{*HQN_oXB_MgxAfre zt5LSKC=!TK;okMvN$!8*nbj2z@4_^SnX}FRd2LIykDa|=Y)|mgd3k&DKd{Gq;bqwH zi5VQ`LEi+@|IKPvsNTs_{W~gcqu=uabru8tV_GlDl&2^9eeSJ2`}~39=lcQA3VPSf zyXOzGU=Yw?XJBABx9ft#)6;i6*bMTQvg_{`%sJM|b~i31yNS@z>A(F`avv`=#+&`^N{x8kT3NgOcANo9dchzhZtFaTZT_ z@3!vz=9jNuzqI+E_3KxwE_b855&K;o57X&8*FUv7edp|#((KfC+NWgnF2>~LR-V|o zu1;&Zyvq7-mwvOo(r8fccCch%U{DZLn1B7m{Qb{nHeDBC*m*wg*CmPl>IR=atT}Vm zar^$Mueo>KP1k36T#)!C@!FpUC43X?C%<05`h1HO*8@(a06qqW2K8J~h5ZwkXY&2B z5oS{6PYQiD@8spLJ{rY0cC5@f$M5%?;ivx7mz8RN9ba)XHmEm%?VYE>^yGV$nr+3; zrUy@Vhfd2~aHe-2Cu4EWnGiAiO?F9fU9UCw+G=s>2@V=@xf@#>Oiak7VeF*|RdN6M^WH ze5(89Jj?oI{hy3I)d#(}Ux)Z*v=S?ic6YQL9@U_A2f}?c1gHOA;-`Y&f*jKRd6LKDfF@<*%%} zJSRhpAk$L@28JD3X5Dih9N&G=YU}!iXO#X&eAqUR)0^R;t#)adeno8c!@2Sd>v$km zsHRQaZ(f~P_A}C~`ww@b*w5YDrrYiQQ+!SD_-?bQE7LE%)=7PR_Rb}Fh8ePcK)VeIKXbvCsB1yRneY@x5!# zD^&b0h`YhQjOoBp1&C9eC;U;0iQRA~ZIbYho9k2~^bS;hW`F;VmA~`607F3_#}sA; zh6js2IOd2y&1!n8v%SdhnX3Fgp#>Y-SJ&M5e0cZFPxH!zVWxRIPx!N`rs`#*5cfCX zH#=p{FUvmW6BeSg^HW6}2SW@8#Ca0IA6|1OzU=lcsa~0VHEO~fh1*Xn?P7O7Z&E*> zHrZa-W}5BhQ;acO5Y-%F8=kEFJpFYxcSLND=3aSj$4}nhewOg&v-scbeX#N41+D|G z5Wk#NPN)?9cKQ1CB1N4Q=Re6#fB#7C!h^Ys-&fSggOsU4l=&(rREFB^TCjC-B=>)- zGxGmVw^!Q*ip{xu`dh7e?Oo6Lm9@sTZ=((W{yF^e_3_Ks|6KUNef!&`4}Asdv_}-LVXl%b==BYdDS^UqQPr3b!;pd%uHI`G)zkhf8 z#J_KAYyYPGn``SbulaoOhZ_Cc=GPDN$Cb@v_;7<`3iAQx4G9jDduOt(*1BzQe%8hOFpV~HEd-n9spDqjui@^ypp;)ixOxgqb#+|%H}m(#3^wdi%hvy7eo$xf_eb)^glDZcPqSTP-v7YJ zeENFv%h&mr7kvoU=6}EW%vs~h`OlMm?aw`Z7xpgxSn6pzaU0g?If4J~-9MY)y)mcq z+BY%z1cn1m;Ie1iv+YHZ@0P8f-Odqm?|9R*;)Em3)2BaaWnCqIdFk0x_CE3Fmu1_r zpRli9VpP7t$lQKOrQ&o^gZ(p4-O*>co|pal&HYG$-+MRnul?(^?d7HE1xy7;A%SL` z^Rs(zOxxivUyHdX{P#0kz@q=W;pen#|LUf$e=;#*!oQ2@TlcHYceJZlc&cV6kk5DN zc976#ozKxbW%P4o%VO5AWlhO{nt1l>r;F3KS~WXZHk^f&XSzG5Jk@_Tv&#P74fa4b z?iv4Me%*e*T|y&rcKVNdCm!#ZVpOia_l)f+o=@SCwo5Eee0%$}NN&P|>RShPhn)M_ zY@?8^o|jtvjfp|p6PTj^7(KGkZs zzu&pHvtUB+W|O#6vwohR8CtjX+a|;QFO1XnPkj5cp^80WHN?x>+w3-fSEzM+uQn~R zGFG)E|7p{WBAw4~K8bJ2E#A-<`Lu$Ay;7#Qpst(0^g9!S zG^FtDf5((I`TW5)`S?RU_lk82e)?>a-%+#Sz*p8YYW62s?PjdZdHX5;Uy!LY#*k~3JN=iRKfuKoK(Xj)XID0j@h32&=TL_UqyD`tP0`c6SS&#JxB z_P>A1?irzVb2+9gKOXVvY3L3+2D6v!OrR=%QSW)R|JSBX*dbNC;ZE8GyXm>Jm~WJS zlFO|z`{}q&#pB(xt)G_L%-{dlYg^_z?)jV_{@J7@RCK@h`kBqxzzd0?UjtEU%mO{vt@kfggcQNYU1)9w&tAw^RUT&_N5(1 z`R$IB&NzLeJy^2(1H;DJ6`$8KFvN8(4F@&DGjh`2_vV~;T$i$Q>hu}u7xO;q{@nb1 zugJ09oXhIhB~;3{eK{|_$v3*Tops&u<4g=UOuz+tg-`U{o4+5;VxDGP&GDi5<>ndN zpY3JUHQ#gPe9W_b6JMLNpWgnXA+1jRuzOQ>;e@w}0elS7?%;IM|I%&S^D?f8e^K)o zswFlYHN9b9(J%jM=h3HWd}gxcKr{2ALK&PUWet;#9Axn}*F!&4aHk)PVV z*?fK7$*I+6HlNxq7V+zcEz6X=ls}E%%11V zpTaSX`2d?BsHJ?Md2{6K=<44;jVo{MoAQ=*+P%nx+iA=1pV($|^5&B~tMAq~@2x4a zEBIKI^U*o^?&p=hzxL{~vohR(RIn91(X+Syd@Hi$_gtGq>A9i*^qQxcZ_+KUvp)&4 zG&k&L9amhP#tt_2o7;ZM8W(Svv-Klmf-)qm4DX!SmZR(NC*s+Gx6`g^&A;AL7k+wu z&fAA)%>66Pb|!~e-dlYC#J98WOMcd5J^z>W>(;GH0Sq6WK-yW&o3_u||9b24`^P57 z&aTN_y!lkU()(k*Ij4i;X4m9qS8iPTjWa**wD>wovo(o)4E&JhyWFkavlRcV z%h5IXv%*XwX4k~++qbqGZ*SVFyLa+K=4+b!rS6|dz2%*+{;c6=_&3HI3=Q9VAaQf+ z+O*i6OSV6^pQ6h;{hsTEqHO;3d0*I%-%HM}EK=UVc74N|Ynxxb-hRf2z2SR5RL?Y~ zr{zt>+r(n3ZX0c0YV=+A^tw5lo`&;nl3f#A$EsKIbL#Ims_8T9&qh6C`0x%Il{53+ zJb!SReUt3;U)%nCKh@+NJu9=`xABwp!P;#h@}P!8ulyYA^^5J-r~cc%&4l~)E9L{% z4&e08pQ(TQkdVap-IL$mI4wPk$>Vdgq};ifHv1E028;iA-PkSq?upge+}oR9zRqrX z#_-`ABrFyGF3mZ<-K<#Zd9G$grE-2=Hsg8Sr?0Q&WV!9MO*vS)<5=X=?B`9-%$XP} za=~TPhY8;{$+90jedlD^9^V5+`nL}ro;iKP9?KJDZ&<@0o=TrO|FL87e}N0@b6y%V z9Poz3wezjhWp_B=rOI3EoVws0d+>zk&Xvabzjl3ps8BIgcWv+frR4`6yscHboq1XA zQe4%AKi|bn{vZ9aRh;1fC!{3sh>kjy;LW&mt<{OLKLPj7#BFOf`kuvplW$twPNi=j z-fQX{{ABd|Ql%Ku$DXE%v6R6K&}%FS$h=J-L2{brxJuJx3ir#CHKYB(dXZtkU|0zhAzt{E`~^tikgAHim+!V9zn^IPc1SYWp_5eGf`ySt=A*PVb+-_e;ai_shS1 zO=n^VZ-XRZuIwp~H5Z>@lukYPN!~yHK1bZ~x?jK2xTe(~eN)76{RybXxp(T{<>&G; zPyg5L%YLiwe)Vt3=B?NNE&n;+?0n{&y6YtsQ=ge%zJKn|z51xQ=(^DYa&2m2p{k6E%7Jv5mT>k5CT%OhU|Ftk$67lxDchbJub-&8CPtGr^pLSp7 z-^sU*4WJr!gXcF%Cj0qJ`#<-*6mPozG3VE=nV;TF*8KmDg+Wio_!J{Uh4XL!{~!My z7XSY=KlI=H{d1d+%=f$aX!c99*Uncv%Jc=_sWz}`K%{XakNE$a=rv;&L`em>4~&o8U5Q_(s4X&0!cae2mv zoeT$Bl>_(~4oKgq|J6Tl^`F1*mmm0W_Rr?lrEk|q?fbl-g5O>Lw(EhI&#q^aZbp?U z3p#wi|HYt`f8Oo$ay!Df7vDbjM)g+nZL|Bk|G#fJ#`vi8tly#KUDqSuzACK9U8}b3 z{qCC|ryXbb{L}7t@Z|r0?f=NnFZ|qc({Wp~gQc8Q>btKK!z)5Q2kBhCE~8VgSRq?H z_ixR=1^$c;+-?hG7#iMZa!uMlL+R*z|LuYDUmA+|1;2ORvt1*@_|YhE_tqb=oe|Hq zv^Gv$mtJGOvN69tbaTGR^8V7CiU%lfai$9!93wC?Dl+NhnZ2R>V<9?NI^ z{m(c0TEoo$e-nSRfBISf<@~(80u0mB^u^CylfB2)w10j7o7#PuKD=`0fX077%WxHm*xR>NACdvFO zQGLGAW*KQG1-=8TWmx>@oz?sA!ZBn2y5}sX8Dq3S`EAd#O5dWH>8Ea-FShx;BK6lc z_es%y!u&K?dr+5n;lgbf82Pd`^TT}mLYka-!ng@M*SA@UcdT6O5015Pe0@%HvjRoK2av1 zQEwZ4YI*aXnP+PXUSA2T)2LXf+5e3x=fcc}pN<9dpX(fEdLRT2nXP|+UVdpWf5bhj z%R{@nZnf{GxV6l7e}Apmx2)?&)zfV%-N#BkF5B1Xapv!~t4DuJJ)M-Z1t^{SBASt=Xwmy7XhuqUcAn)PsyT-fceqT1a0=_|eg@g)i;p+Wr6j zImtfXPTAupOK$Go7b|;$_~LsdpS~9}J{6zqo!aMM8JG3ydY*1VowCm9qH}*3=gV_K z2Nd@7-JM^bR=la2!9vaJ`KL$Q4s^W`$ek9$zI1(%((9-GF{@v9p7zw(z2?Xx`DL1h zPj83woKFo-dN^I~M4n)+eBa8Sl5?`99RFSmSJ8htWkyhb@#&+%3qDH8e!KK3qIkpK z`@hSdPH$SC<=wb^?}N~7A`dK1%m&wt>o+ZJ=VWJ$J8W|1S8U|8)PLXo9_)K|(4@f| zG|Jp?z3@u^^ZJ^qZ+=;KB2}mTeAoCP&3I3BLiIdey^S(ne%rS#^^MZ@o^m4d%r2G# zx2s~Of6BVQ&E@IqEd59GS+czQzB~WSw=r68wMHY)^X%97M=PTGA6tKa&TN~o&u34* zluN4?~hJPotZxKe@NAZKim%+ zPuKnW6~*v?2~O^^!S%MbqPE4{KlKjqxh-Nrt-m)B*BST9eXUhBDrQBMDLeTLoZ+h&_rlx|*m z@2|7t(dDhb-+Z&$T>VqQ?|;ZeLrzI^d*6Avc5D79RTlLBxc)S8n&~a&h;_LZe%brD z&i>hZ?AOb$1=RpL_TB^-Z$oP2o3#c2-|5H)LpD`S;hh z8ip6WHfLu(o4<*LyJ0Q3aL-*ps#;>Tm1*x7c6l z{eG?2o1fIYy>lRbK`QU`n1wN~)7CDli3mvjc~xM${+B!XSNyzlnkv_{@2feo{Fjw+ zuE*ZCV8%No7#a+2l^URFBEiJY$Zr?JfjSeqf9nD+H|Lc~@ z*~PCn8gJV$fT#!eX`C(Y_EJO z_-uRs`<&I21>>LYX*+(kELnT6jH%zG()ju7bkDw1&G=blKk;qFY_rD-w~Lf_@Sk4y zz;olwXYqdV#RqEm=F}@)|LeHm{LE0kgwvo_$p@<_>o57I*prW)&)vKB{NuhG-#(Q8 zZt(9szkQ2B<>#;dQGVk3zu)NhvhWBWt-V(MdB&D`XY}*4y4Oz$jWUwTpM1MrHQL73 zF7a;1x7crykIS?k@9Y!&7n7~lcaOutCN+BZH}j_7cTSY;DcreHH5$|o@2%fI|74jA zONGN~ex|<*zbyD^UKBeclrP~j#6cnNmK^I1U8>`xr267cPU|G0$=`H~K5biLw`udw zk`KE!wog%ge9x}4X8UJ;j;&|CAJ~brT=!V7!@cy#qgQKX(thmYRo@bIFQzE0^1i2@ z$K_+9m&5(}mgrquck8;|{%z9sdzM|3x5|Af%WB>vyp82p+_uMl_s&g|yI>=H=egUq zX7*hbCZCz@xM%&3G0Lb@zuw6Im1RRDI0MMO^^bohQW#&p$8G!cgmO-q=T}}?ec$7= zQZDI=ZQa_9*LMCowkY*l`D*VaQ(Vs|Pk47f`)^O+%hOwa*nHaNb@AkOqjNgbKVJ5l zE`KFxnUwb0h(qDlpWeQ0wtbtj{7%Tv-UphugBV^V-(#!0rk@i1Pa*%g!fiwSpT)`& z5%Y3Z>IrEaSDUinr@!j-bjuS@7xBWJ#oK;9Z~yG3z2&b(15Yh^{qN;Gsf}4*rv{$d zbzknlxvd9_^S0eE-?lmCj_SVan_hYS4>UGe?`*UCoWcC>yK=M-XX*a^{WU#%TNTSm zh97e}V*hM9pRK=oiFah((xY#x;_oii`({-CW97YnXYF^|a?IQ0Tf1Y?29aZy@~6vW za(+(P{?Yp8wD}y@*1dhm^Wogor;*PZe)h(^yQC8xmBz`y1e!mHyZrxq{{KHGMT-9A zi3eu%b`-7Cxinop)3z<9`R=9vA-nEHtV`jNmAB2Bm%Tu~^bb$K*3!eaFYeZ_d~Eet zYqeAmB~Et6k&=Wnf5 zt9Z3dY)i`CD~Hm4y-l^gceHt`^-Zy9avE=9WuvPtiUkr5FEjdO9X%_RZ`S=&sg-Kb zVW0}%`p@?F<(4&kOSja#bNHO(g?Gk#lkK*$Z=bzCW$Vhnht$)yr*$t&QHWmRvZz{Q z_tBcX%)>!1cIj{~elG5?a`Uan`{zxtSfzJ*%bYd4FQqTJz39p7*61zgEw1zY`MyN& zJm;1-+4CmWO%Xq%)}EuEQF-{2cJtb^Z)#slPBv4n4St`J@UrosjLQ8W**(G!oNnlR z_Fuw&hQCPinb`+t#)e+dAj^U8AJ+eS`Tvva?UUU`?RUcd_FZ)~a%G+NVe7GKe2zdRDyQPist@G~96|6(7&rUrzpg^~>A)UHZmJB|nZ&Pds`4ThGl0 zhqqnUFF#u+>fQI-B|rLIO{K4P^wtRGz55Q>B^TSRdUofNT>W)B+1d#8Wjb7w?|*aQ z$zCn*%_dX&)4?ydR#!aQOigX&^>(&x^M00J-hcl8*ZT6`GZ|j`ZF_3D`ILAxcf`5I z`Q@g#Eo7aNuH{a(hSh&orSS~;I(3>JVd6omuz||}7pVjrh z&hO9owETZfm&W~b_SyWx`rh+@C_Vjob6)DaQqJ7(slGZ3*4jOdsW#a&^=sIy|I2;` zX?*)_r@d$0- zD(9@-=F+t`F;9EG$DT!J-duZJ^>Nz17oBHi)@Lt$Quq1!kJA2*=Q$tiesEkdkFWfD z=gg;6`L)Zpo^QFXdLiEa#Ak)#gw-dz|9`)KV!u7>iTYEso>-)>k}2P`cfr%(`Jwxc zE_KLzDtq&R)zi)C{*`M#^`2APFZ_TjV#A-~oA#ES|EQn#_2H zxchIve2v+5IDM-9&eSF|tJyViWlv-Ge|~U%)85FQ&&*xcl}T&P%46Wu^_zo7BCo_V(08SVvtj=nk1y7K$JiEsB#PK;aqNBq;5 zGmfA3=A7OgBP@S|Wp?Dh&YTNZzSU|lY)}Lh)(jss%y#`bWwZK^cBRuYhojs#pPktk zU3nZN_@;aLmxeT}>;0+K?-OR!DjpEs^zWM=1A{(fY`Z_RyK$v7w_Ln!w0w2<>G(bU zso{6TreCWx;?H=~c;NXa-{_j@+#lBEY>D{>Uv2Ps5rw zZ~rte=gVB4&C5SEJj=eBR`BNBv=t2NF16jZW4OTsidBXRlWlSz=H^_!etnnBv68sY zJkNCNcFeB6FTY~PRaG;)z0ba$T3$T+^Izqg%c2inopI_`erfc+X}Jl!bqp2I(V3j+ z8tWf9oNBM9vYsye?fB_7`;42vm*!mG6ZbQ$`DDJ&@0_3Ur_9cJ|K0Px-MAtmdbZ`> zsaCZD3n5*PS%s#ZC00;X}_OYyW;uUoXPeJcFqEe?hxBo zt+>N1ntRIowSQ}KqEAn^=Ysh<=U~|MLo?n!u`&@>xqZrMgb3KVM(k=<446 zVhlF~AOTvkP2^bEb*=L1mj^$I7dh(euxCH{eN!&K?N-q;sd&%cT5%cHn7zu5Cf4 zan*C1xznR>1{FN9(|^(!dtgn`cb{L*v(~cDdtUTCM(^>#Gd(w-Tz?&XbKY#;J=!nb zwk3C8=Qtqj4jw3s{-nK==l9EOzG?e!BptYOZQH!&sr#p#F8Ix{`Q%;oBFS%;ufGjT zpMIY4z{~79jn6w{jy2Cb9P&)>p)6|!^EZZ+ZsTe4xtfc3>z*+hpJL4611GwiV!mSHH$xA?~UmbZ^|y8 z@V4?y$ky8?`ns~ z^E~UromtM_cNaK!>Q3*}*ZZfQ=9#d2KKHz)<5A~chJO3h;Jx97wZGl;-pV6Sw=q13 zvln1sU`VKbw$$R8WI^>#pWiRD{{<19(`SBFGp&8%>nH3}`~I-BEG0FM zZ`=8&Z}pc>-^pIP{7Chd)^dXfiJ)Xzdsu$?rXNoCl&dqg9bLNP9Seh52PD;`^Ud=! z|M9t9=U+Y_AD#X`o{j>n{LLf6PJJRvn9g5Nd0#0^TW%7fBj4P^?mdAj|VQuRh)JFq-*zN zmng#x1#p_bu|%_=!2Iru^WI%H(_e3$zWk*^{}0A_-!=I&_Dy>oDu3Y3)6AbMAFP~t zU$sd2w(0kLdH=WPKCk@yvv-g3HnpF7?wpF-)|nd4kRy~0T1JqtdD(%3d-6==f0WkF z%PsxcUCAl7^Ni`Ik3~8=KbgcHYTx#5`TEM2%kM`u{O+B?U-oZrPVr9Ba`#x44WVbi z^CH*I%I`71|0Djhk&6GxZtfof+bg&I?u|LW>yH0jbDf<=Gtv$I2kIR!|HkmTdUwOq z@Kv*ap0>OG=-j?@b^99D+P<5wY*1f!^mvh_{JLswh7Ey`M* znzC&c?Br{I`8vGm)unreg%kF*oSOZKJ$`ypUa{S@PX`Zu`^j|u!G?q9moYRPxTFo5 z9JZP5`@^Z=B;O@_ozF@)c+Sn|*1PK;`RrllZ2R|4zux57?2Be>;05&~85+71j3>_Q zESvdkDT|(7LMEeGnsWTQ=PV}^BdVT%lx?w-IdBZrt7ABzTB%pF2Fq#vQ&-QtntSf?OaYz!EZbR57WSRh+P{V0Xs?+5 zn)hrCzEGzo=igV0*q0k_zWRF8)AFXZvzniXe{S4ZAyPcMM8IZA{<5l*&Tb6ijo{R& zCv@yXkTzsSU=lJF8+nbJmd$V#4f9}Cg;!VfDH7Qu` zTfg$mne3^bH@yD)t4TGSAqFy#zN6yv?U&2fTSlB?-)h_U^X*srx-3V*YK;$0A0p;` zJ~+1`xaQe`>aTC7>_2mhy`T_WKRn2~(fgD8ptF?+|0Mg9l7Gck{N1_X&w1xr@@MY& zRQ_Meke|M8_a5n&cdb0mhcoQ3fVeDFr{LtSr~Hq@swVtV@V`;=?>Q&+a_) z*RNrFiu^mv># z9@o8Vd)A!okH})>2We6+KO_{xu#N>>*2nDKq;pJ$#gb#+dh3^s6V9`&KYHqp&E`2b zpXNVPs1^Hpex_?*`;q4{HTv;q-rrf&#{^x8^&!Q_{PSt4etC7Fh8T=vD^XDO zTKbt$x%&0zdB3XkBulJ03Kn|V8`{V0-DY}*a{_b4CU7ETNRLo>Qub@s^<{IJXT+aK zWp{q3!aViNle-$)#sAK=dGpV@@5#U8?btpFZm)|Ts!x7SM<(1b&vdhrI!gP zuzyJT>i}9Dxo67Ry1!TdEL|n<`~ROymBT}~ZP|Q9XI`JY=NrFY@kL?enlpFL#Rt#4 z?X90}zq#IiLhh{7H~#ST?7UNJJoj)s_XiiBr?q;&KOfee`6}nFvfZS&yC%oQ*Zayd zGJpf5;r-Dj#n0ELe?BiJuyZ0$hfSEkX9e3AhRffUPxFgulrouLug9OAw`~1hn>dAY z(?8DK|LoH@_NH8i|7W^i&VL$f9b7y2H_Q6<@+TkLCCq*Oa&GP4zF%Ani`77mzb85S z@9%|Q8cxI+Rs7Rynt9*z+%4N1;*6)%&oLF&Yc5aC(|`Z$;918i%hjpxqtkkr^N-1u zRoVx>ejRu3-mdu(zdC+a|Ken*ums2U0p^Vj&+2~t;{JX0pQyg2PkjBHegDe-O;=#w zr>|XHTzUKUdb~BB(C~gG=Z7P2=G*^&ApdW+ zy>0l^`ER0b%YXfmIQxam8ow?7?mrDbecz>+{W5=U)x$rlE1Q45e?2SY+tPpGTd#Zl zx9odbZ&d1EJA2nwRgHhT$D=Pjl-^dj{&M2m_p599*KaR*H6d;5-kjVv+H{9uKT*?DP4rZ%@7^BO9N6n}6xC&&sC{fB2;6nI%(|`f|Jc)sm$??0`v0l&+UIs`QO@`c$cK?zWKYB}0H}~?&%eAKG-^adY zb@YE#aV1#x_Nt;YpY~RzYF+>I=4a2-XEjoPH{CoMksA8X)V$Zm{-*o>kd6CwR>$32 zX7ghG+tT$S*Ua|$wM{BEJAQmq_VxY$BFxr&jracBZ|3ww#roR*?`&?_(%G4-_db~U z&D-m*)!NfvZ@FlmsI9tvv5luM*|k#ht*1zTTu57X*2N?iSI6#o4vo{ zPfbrPu5{E6zp0h8)8Vw8OV-)-H*dVk%Zc7yckkY|ThmTv>Ib|kyt_SL{~lXvzF|%L zXWd_tz2`D?%%d*NJuaBNds*I|$cy@qr~2IgvwCrw?Dyi^k$2~{bt~-a{x7b!9}jaVy#7D4dHW65)s^O3 zM3<-67R{S^?y_;m>+6g3-@N?9TQ+ac)gSk7OP{S>V;p!oBR%7&a&TMPn>*#E`!_|3 z%g^oS{bM1P`}&oBUEkrC{9je$<8OCe{a*IY?B92_tug$u?{BZ)D!+JY;hyVrQ?1wE z{LJ0=ar>Hd>)mXtuX}De7b$e=-yS=@+TIl>Jk2jD%|EhkXZ-PJ*HblYzxVv#JX5lJ z>++3P>QCQYVV`{Z?a?FO7RqKNi$rmu76oc(FGefsfz z{qz3&hCQy=KRnO9uFpH_cw)~sqkq?fx{v)kB+Z*${JSpckG|EE=Q4}ZH@RlXPg}qK zcvSuU%lH3TW+5h?qJL5L?->H)?OHcpxYtPPYj&VCR&t7zvR6HX1>W6mST=PYR zr*3|B=g<6qa$}lw{;8xE&D9A}`y+d=|Mou4us6+M$@{f)lI8dDICd6s8I}o28gHM| zbKju*M3&ACC0lpNV|J?QOV++iYs)s^xqgiIRqF(!TOV}3DzwhcKUPtcv0Cc))X5D& zcUV%hT#p~{ljL}9RWW7vrOSqMmwJae?!94gtbOPGS?pTr`Lm7{{xF!4H}n3-V%-Un z3Zjz7pE%DlmG4N2P>bKJWn=U##dF$}!uY)xBok#ftzp}oZ8j* z%)$Isk&O1`tG8aB-IH?gQ}Zw0_9+!XynkGOhn~}BKRQp-S?_A_mY}JfahEn`?^aCM zAoF;|>s?aMZRwIUA%bFGX{%_?}c0r#__xs+4 zSY~Z;nE3v$oYigjk7bUxUcOGf>Y1UUcYgI9CH|>v=Bg-VyXrnaT>A0s=2v}RgU)^N zl$1CjRQXP)?Y;NqfbSE-w@yu%<1(vMR7du7#!t)J>z{62JNLEhT7&5uf~7w#dQ+*v zA2;!pqW`Cp=CQH2S4`cMwN&ZFZJp}S6rQ^N=PLyJ&TQ69?%tGNFA&=IR6is6w*JPz zZ@!1;w|_fQ7AIFUea-q*`^||j;%!x*?ux4H6ONsmT$b`QsCt3!xtxshDod+X^Va@* z-sK{j*EwaAfU|rc|G#f+T2&ukSlPz@4Go+2{B7SPLr!_;wajK$XS|rz`B-zy!!!QP z(py)(39Gk1w=w5_FmG7ott~9KbPfbJB`%%w>ITO&t9|P}2X5cHF!NenBMIu7oY-(7e7`EI{}Awa@um zJJ+0cmj3ns#Da}EYna=hwm#i(j5~8l z{@mvi^at)-Cuk8HL^VDAq3)Jn=ozVcMoU z`@YmUOPk49t=isq{c6|U3rSP{?Vnd2$Nu~7E0#6<9oc46I8VOQl8cyXw_@7%ZMz;{ zFjW3Kqio*IwkzLO{gZjFy87e)bDMKDDwV#oo!PqW_;zc{x^L$51q_Z~zQ9t!^zU;0 zm-{yJf3^58&$s_@|0-j>tU+|Y`s)Wf_N&c%@V)VY#e->YME?GkaeA(?xZ~s0m=vht)E4%Mkj1s5Er+x*!*?n zsnUWPJN>E&B`Xb+52zZ4KYCzUpr2~Uw)607+xEvs*RD^USS6#jI!My8-_risos|}* z`u<`(Q_JG_e%hoIIQ8>f^~Vddl}(;(o5!;2I77U(<#V6BE0e9f>UVzp#C!31RowSI zkIwvSd+t>yyOyVFakXZo>j!GCo#t`! zSB});x7(I4aJD(V-tn0;%WCi4myD8f)azsHHCC>dzpS)2`MGy)UhhA2; ztxKo4y1}9j=}{ zUnh0*z6p1yj5lxm-aHBZ?GjE~7W(|&;D7Dx4XyUaF{wEcZSB09SaNdG7Mq%heaMuY z@^${{h_o~I-k%F+9-YbG^=hl-b>0dA7A!J+1zQo#{GLkDwvgTuAQ=P z$-MZui=lOW-xcmP_Mctzyg>W9&$YH?sdo*k*`9oNo{+2l_}ilI*Z*Bsu6Dm1zeUc| zWa7d#ZgJ^Wzs%o$nYi%8>Er(=J%9Oj&9SZ0LEE21+CQ%-Uz0My`1Sty&p|fF_D-GO z-md!hpYrR;E{9c&So*wWW#r?IO8hwURr_n$+vhUTX|`8CnoiqxV#AH~UsV^GM#NdG zS=xTfj9n9cf z{<#I6>YexGT9 ze-6EW^7zOx-%qu34cZesfBrC*g6*@b1>d8-I7OEr6X;=IxO(!U~~?&O>?cjsD@;J(OvPwvf# zw@lxhCLFz&eemYNs~-#&s;$a-Xs%_r>a6yY%DI`_Uq8uz{`KwaeYYpDua53l)$X@j z_kH$?NxHW7n-yM4w4BnevfHo9KH+cps%<_8^zx?HZvW|Z_TYB6119YI%90nweJYia zxGuQq$xXAhU+tR~u9~NN_WRtxwmVCwO}_9jCHao-Q+vUUAFZ~@{pP=3@h9%lz71EN z{&W6(>FM^?c{3(WZ8mz)|0pW2!H8LRy^V)Po%i))bDwR^a28fjN{@)dpS+jBPw1!g6B^TS$cPD+d<)32SeDnU6BC)NE!LyUEeqW`lKjEp* z&9y1@BB3XPZ@2AFcXN$?mAXZ@@u^zm|7gxh)0y^)@a;Cu9{4b}#37v#&q?Z#XwsJ^An2^u?!-b_i!Joi8Te<;4?m?Bo8@b8&rbeNoEBi{^f|jjqiP zY$*%8afJ_SE&6Mtt&5Q%GsWywJ0QAw=9BsB>)+e<{9o~Cqv!hqSK|rc+qcehO4@wG zJ^S$Od4BvFlgh(av*_&4(Pb9c8vV+=d-cqVPv5Kmik|Y^acTLpuUpHC?}sh6xgBo3 z`SvIElUu$NpFJbZteh*OHOKSw&Cgp8oZPg3(u0T3_iT*nOUySvJG1kvO<1JavWw;? zvhNAY1WuJOezGEd^M;P8%KMAuj>pM4oNV+vy)Y`fkU7QNz-~(L+U=X)e%U%vVXN?` zD^qhMKSjQ>vo($4Qz-g1>*0&n?~Mfmr?nlqrk!G(9kui8ib&~+Uj7FxX5aa=qDFqb zbdaX=zb9*(jx|KN+?pBm;_A&)J-3*f>w1@}y{&OuyKdz?G0XdLs;g`EY`yYo+m>tR z_N(3dTe~Zz_g-}RX`ho~r)46Frf;7X{d4X5%b#;k?&A2;a@A@7l!uikmoGkkd2=4m z=A9)T(en#SdLGTbz5e#D&u_!eZF}=`()z8J_nhD5u>RlN%fa_gZp^WImmlkXJ8Rm4 zP@k2q)v+DXx_9Tz3)8QVvC_|7TYpn5k~5={akl(^7u#c2vo6MVivPad)jmmOX3vVP z&Zi}1@2&dsB-LWt>z9_HUU{n{ZStk_KjyD?>AH70XKPT)=Dk~f)x_7Xakc)va)((V zbIr3mDYdr0?QRupJhw+dIA{6-PumdfyVHBFzg_Y_|6ci&D``d3&IioAfAPw#Rd#1@ z%dMTXO|ew{chu91H{7m2SlF}qP4t&_t9QMazI^Sk|C4%7%ntos^sD&n^w`heykBpf za&_v5Pg(Y+)#lC9*iEOcySjV+rnhgTQ+9`~-o&?DQBY;l2t zd>F&5{j#ZBQzOe%zf~T)z;LZ(>i+46r*gfnUvK;OLv`mP-C2uctG5Kt+Hz@IRHW3Y zY5zU_HyH}4sYac9HF8{x~@92)SqcMDaWjBj!YjPvQpT7Bd zb$)c__Vas`?lnHj^_uIr-f(x#*I6EYDZ3;59;TR8{@Hlt_{X^#r+?U&TkUx^uXgR~ z|0iF{KRv(y*M7U7_h&@*t-i{#Bk1$2C&%sozx-}w|F_2TgX{4JKR$%T{EyC=rPwAD zIEP2)QJbAxZ)Li{z1c2B=W6pG7fPSvJ#M+P@Eddg#a5XM+dm##XLoPibL%%}*{7bq zKkY#EpS3JXpK>?pem=tF{!y&z{?i%DRpV<;XqkQuDsufg&wAeHxjWafpM1)+hUwSG z?GpY+E4SO+oD?7^9lDxT#YiC1SffvQUtOYS?=+Wtm$|MV{HV3Q=z+%S%lTgqO`pnp z)ci|{_nB8GmRy<5aK0-}@0aiLY35nSWK%CsniA&r&D0_K-0eJHqYtxR+8a0MIoGZ{ zXz%TK=guw0rEA*{{?#~MBlN8K)xv+bO{1Dhj)(ruf16_)d-ZpfsLk1>y%U4>oQn0f z%-3(&8duG;eC?|JPn=i$3eZdT+12H6_1AmHmLEIYa#KpVzIkgufBdrRd`#@p^;Z^$ zHLplMl9b<&k@tfb=c4r98Ub=0m zvtdWt?N^hIyt$?G=UQbKtK{DQ`d{}yn|fuzQja~ZDHTg>=ESSj>`>ZvJ#GEejd~s| zEhcHpj_p@{n`_II{dA9w#k}jmkA7z`T}?hb>E_K>{1=@fJ5N}wN-tnje!cbjrrnd< zHGKV!|6jiJ+PZMNd;NR96u(^m>0|w~B-{HBIWFpb**|y9|NCCD7efDTKYV?gN)v)6H#7(7-^dVD%n=Kl1M3i~a56WpbayKTGnziiS3G2@o$GY=Sr zJzo)T_3fcRMX-q+@NynUASvwmmv*FK%yAFVcho>yvnYjt_Lw|wgED^h>D z6yhoq+f+|!dhGoDb#C^))6So^WJgh#o z|L4A66O}E$vz?4Sd-e>6?D0RP49mVPi;U-6GN*Xi@y$7=bFM!OSj+o7xx8rK;kx!6 zImXM@@YF?HdzM?yon^mEs`={QFY;>yTUL zQF-^g&1-p7KKCW>QSLBYHvQp4l@wbe;rfpPaj$MJO6~S>z;+~yD*z~>cc~6B0H}I-M?p~UgVy1N5||{eqG+$Ipx|1cdht8 zOZ;WZzj%3-iZy0%xA^ZspGcrBw? zyY!?r<7);bHj`nT5+Pe0wY#%^s_;58%f8nHz`{G*qi)5??HJ@ppTlxNr(&SY1=9iY~vqQ zOTYfVYu9x<@05y}YbvXw|ApL2`}#4i+jxVO!0ukRr#1CDmNBc|^IWP5GUU=}G_bvV ziqC%ArQ+?1H#ewLJ3CpEYj$q03V0U-EB0GVd(=Nvo&54)5Qp?pmMGHe2`d#P*Ll zpG&+X|9j8L>HBZWx4>xGJ*l|t)ob!6aYP-RdhJuJc4d%vR_?D~sW0wle&N5h{$au0 z6bVjO{(D<^G+c`Q=tq8vuKgii-Sy}6$9n1Ym$ZIlJYV!w<*lQy<@S#cUHA5U3|MqM zem%1t%L-nnHyir6xaOzE&YDoObXuyh%jY?&ZJ}q+FPU1l!i3>zc%@zKEzfrw%=u26 zMoce?U2gZfIx{gWw@f!@ZO{L`*JXEe=v%AiRvs}-Kjj-RC*pM6DYy1l>(6~M>HD7@ zbN^IC?e(VV4~xWBH@)AVV|rcnRNUTIs&l_OCR{1cFFx(O)lmM=mykcqb=iNnpT2ml zQuS4&!mhm2(^pzdT>doXm+Oni|35XHcwOJ!UO!F#>F<42v#xdr{eLh2-@EVs+h0G# zvT`T$hniZay*_;W-_h(+?e+G1>t69o+x^&lBAh8klj-RWug^K3R%+Ip)yK2#H#)Mn zX2zq#M~a$Pyo&X_=kj&N!XIjDd303SHDUf1=%>^^B*`BfvaZ2{426KC~LS;BXJ7O$sivT5Oo9Syo^XH2BG z^DzICdL7g`Tjk^>VSR}-q0^rKp2X`cz2(Ih?W6qu<6E)99gdSYDy|1^W1YCzVB5zJ zo4kVf*4XkT*MFTUUb@9jJ{g9-XT>Yrd+teKGRM-1s@$`HABCcN4z!{C!$^biv)**X~Bh zd`h#;JMl+hCwuSujQNYVicEaCDqB-&Ye7n6-qPCsNek;1L@~Ba&X#+Xv3kDu)BHfi z<4qC&Wz+4S35K-)ePUk6E&MmC+fOa4FieX7Mg((^f7;Ir37vQHw3h2OOx>-qQ0VxZ z<65UzUujrZ-aN18MWvs&SLW#@@AcOot%!X+^=ol=PL|NuyN9*^ChK0|zFhF}Xz|s@ zF&l6DG)!Z3QCm56!$kKZZ(3C49z2b^HKXq1jpl1=?_>V!|IGci{Cz^H3csVBX6NlQe~O7le*GWEw|M=^y%l9qr7sqLoWDfL)apij@bCX- zS7v|ZE1JG_X7?v4Yh7mLk7c{&7jHgz`sKRng4Bq`SDPD`D(Fmi_&YarY5H}moCzy7 zPF(UUce2&KOP{`%hECx)bKUTAki-%FbrFw4^{byGy{-J6+7-DlY2oaL2exW<%U$dj z7LDB79#O@Y|JI9VeS2%ol?B%dehA+BrSn>F@vWZdm#?5sGQImsfHg5>yP?; z7Srr&*!=wMBx&E%Ya6yKymw{h7p3Hxg8U8D-B#D?dtXbXKhvCC)Oh4J-_=5wr^_$> znY1-@w_4o)y&TiRSKBgNy!zw*tGNB^xBPne`|IZjdy}{PeSc5s+IQ|Pi@o=D>(6&{ z(;nBq-hbrv$`yR6E2jEHy$vdQVr3Wbahk^KusrGIYhIV%zf<$!>T!9Ff>w?xkF{RT z|Nmw4kA-(X$I6~u!D}3reCp5UYxR%KPFic7b)2Nnf8qD)Yp3?M%!%Bd`rz?wiTVt_ zwC^UonJiyQ_N?6Sck9C~w(Fx}*2*pE&^eiGwq7T!_|)s)_0iUQFR#e# zn62yYR>c#|Hs_jS-es_Pq(@4o4)^e-)ZBevu@sd=aO>tl(S~;>$J=j z1#43qw=_&irxt!o;Q;BxZShYrY+qz*@d@#gUrW6SzE7r*R))XW;0H`dN1YP z?XBn14(GG#Jbz@SdT34HvQt0onGYn}r5o&u)ayIkyJ>IySJm{Z_g_BvDRKU1(rpRL z%Ed9o8>W7&e;u#x+&_8Z1a_vix_wJK!kC}kDv$n|A$BKJa`m@Mb+=5VyqBEVwRg&- z8ETQ2vvohU8*dY?u1HjVZq}!DWqaqY*H4#hiLMmNy6tu4_ASmIrP*fx&KreUpUTnK zRk$5IZ{?}`shYYsXFRSynXu_<&e^4Tdmf8dyPgiac=(N}cYE=<#3(!6HE)}y>R1e})jxl=TAj1)Y^>|skZTdPX;q}$F<+;9b!q!No^1Rp;XFAk z@Axn2LfZm;!@ASmB{qF8H!~idd2vPT=Bpi95^2X?ez|<&fZLNm?Z#PE|7S7(3j17N zQCsi%Y;)SKHFus~46nZW<9c(rk&52&`-W^iH#yeMi#*HYz2?~7P;Kj=wFgz~?{2#_ zIZABRv5BuOqKnL;-kn~TuFdaib5K{_MyB>=o5USYm-an;Ra#!Gov$+k<<{;G+h6!< zaYpaTl{3%k>bE@0yb>%`FTuR}>8t9C7m9N|_9je=$y^(zv32v=gIktOYMaLV@6v`J zXX0;9zAtjqZ&Acli@A3nc&%o=9QWY9-gPzUl?(qJU%2O&=-Rp0j_RmI{#+ZVJykz% z*On_QH?5r?kguv!D-~H)<+FEr?iSmO+}UeqZBO)Cpe{w` z=fCp2!FMSk*MQGyLBGwy9JW3Qp7y_o;n&p*lcrA-j#OXscEhvF%`3v5KUR6AnW6hf z$$7i(B;U9ruNOD!&(7G!ZF}CkZ;PV%TETB;z90FPlONTz|8?4u{kwWM+wHZB`g;Au zzBk@cy-nLMo1OIA74t6b^wlkieygUG*%!xq|Lo*&Imvm}X7$q(%{dpZemi|((E=Cl zeS6eq74$M^#fjQlPT!U#zD4G))ZM4DI#p->-Tysn#~wkaHSQTRTR40w&gkF1QTS*1 zOmXL~oa(d1efHCm?;zon-C z|N88mcKl%2pRG%0N~gX19Z~yrlT7XL-R{+vCmM=bqCW@RJ9>4s-Lf<9D%-jiY}EJe zV*T~YwfofF^LFcAZ=BP=h2vRPbi0n~J$dUZlfSyX>P{3=E{97-k+0ioG%TS#Q(@f*6y06 z@xSfg&U_Bt-|mM#)33`ub!*UeSs)XhnRVPg>R;~H zu#4}WCt2i_OU?aic6i6Bs`Wd*pZV(KdOYq#+>6F##)l*P8|q)@mv2gT%a_Z%HT6a+ z3&*Y6>ah2^+3qizE#-M%8&nwAO@3#-yYTY#<U+J^Y8m1|Satjq~Ay16;h%kD=)bV4`?aSV ze`)8mfR z);{Ve`Z>RL!kn)s&oAJ89{*23)zkakZS86QubL(A(YH3v+opYUkCW-doNgtR2mj}t z-u$cEA|RUeLrTY|szA9(OXl%iExo(NDrx$~wsS`JF0ENzWI5rkX4(Sdd$Y1aujIFX zGMe&jk>%RAQ9H%IU!T(QEB@B2u%p^jmgid>{C7GzH)?Ou>g_Yju1DYMUi@95^7VqB zL7mb6t}a}Y)VKA%_Wb)lkDBHOeyYknAsz95+5fmB`QEBtJJ;Nb;*VT?_fy5zPX&Sb zx?UgGeASF%I(aLjJ#(+^#Hzp}x7&&?rN6GX_t(w+eBoI{{Z*y;$CeduUG4Ey@74al zmsPr5zATMn`243zdj50S*~c#~HQ#Yj)P38Dh)cGwQYu4NT={3LwI^04|Lf+rJ=QTF z=Pj#T9B*_n_{J>@s|;t!_^!3nqhG%KI&Y2qfp)Lg$4t&eA2Z0^w$zX<;G^HNFO3uZ z|7PS~&B@qVv$Ire2Tx5pW6siS`L0mwO!>vVdbzz3Z#%Q*)ONA^Ef##uI9+UQcK6>K ztQUpOZajDA{N9tDpL*2lw=q4|&G{Eyd{W9l_M33CsAj%uj@`;+PAxrtmNy+)n=5~x zSN*W#%6XwL-|82CdJ$kzRrizU$XC{0?Nv%qul`?P+EV9tyuxGJ-_ET$$Nw?zDcl#v z;=gLjlmk~c+5OZ@-@9#LTlaPyL$98Pj;Fr`dC#kki#i>AjeFbUuL-#}FFre54w#o+ zs>{q!Z*-ECdo9^F=`u$0L^{l$IKkxhb7C-EE^tkf>%;j6oo>R8JkgdkC$0opO!oG>BOza4JEpZ&v;L&jCYH_IM;3Gisvh>_M9_*xnyd*k@f9GKXT73 z(&wLh+oDRgEM!&mX+68JRsFRYlK;0qTofH=q90%DfAhV|*KO@4TBhA!s(b#|u0JdH zV%p80{{mKDwPv)PobD_vG1aYoY3!dWx8CcMf90o7@m|sM)^!@YF8}f@Nej=L@0=Oe z2{abPEM0l^KexQ2Z1TjQ*A6PyZ+AQu{JLH1X4+4&|8^pq?Kan2Bymb*uvDHpJNrjN zu=oE->pw7-o|~fQnIF{_Bo@8##iSP}E7Lw~=gYrkWv=s5b%DV5CwBjO8LN3bllDwi zW|w7~zi;32`<^#;EP1O_lQDPim5-bHId1<7c~o_y?~$L|5|+kI%hxGi+%s)$&gB%D z{B4N}3qL+8lzE$P-@U`}O>|rI>K&z9oCGBE7aIod@9pMjcQH`mPTK6SI&0^QqG!KO z&I}Bnw`zGvwL{8w=|v(z`4&pQqa?pQ;obAhF#7KVEBW`UdRW&?J-FwJb;pUeXG@=2 z@Le&HzhiQ{KTAYa{>g2{KW*2F&!0}+yZd@k^8BHY;f=c?2tmE$=xg`2C@K&JraS6+b3p-C2J;=Y?yY2Sp^LfjE ze-~`cF6>nP|Hsj#n=9h>rL@$r)4IW15|@83zxT-XiZWC3+2{k8Zmzgi_1d@1?YG=- ziS_xG%VL?Qmhu~fJ+IPz6g9nV@6}yd$MYsGj4XW{pKWTiYt_wZS9v6vCw~o5T^ya8 z;T`fRLU;YK?^b#9S$$I2YrwO>8ooyFx} zm$5Z^LvV+8fLz*puglk-E2jOIUnq4}?h2FTwRuygY?1g}u_g9V)y~Fro*CCzs zUGFwbn{>JC-lN~57jLn;FrGcP-!6aaf|=i${#M=iQJY$`e4yB)9)WPSNO|Sir%hxHG6M< zu+3tX=2fc-?*-b_bgoY0k6QC|YO&4Fujiw(Do*-q@3uavwnIMDSit7V>@}}KY~4=t z*XE}FnZN#Y?TzzMn~HWi>8@Wi{d>@j;y?0lJ9_``o%`mxVO!a~PuXQ*kt_E2Zv3oy z_J73x_S1Q~*Ec@DGpT>KQChU^otu#}S3IAy)#Fv)`}D8+$Npb)tFm*MRa=}dxToP4 zXNuqN!>oc|1q-Er^RIt>v)kO-`u)V)1vX!c!?o>9eQ#g-(B~j-PFO_K8nb>bCi{ z9ha7%o17&n`t^5_C3J=hfB(HHCOKcUehJL((2Eu>W?6J{`D={C7EC)BveH}ar`@%$+MDw<+GeG0%UQC#)t+k(?=)k{NvWZ# zueSD>9?XvPblATx?$zh-vy}6!i)G#ZEPo{PdWQYKOP_rHN}nv#W_uR(Dr4u$X_xZS zj&8SFba7tArO?mkJiPyk_c~`^>z4YmX?m4(aJqHX?3nc%qu$+a%vrqDPTp8-cDhXE zmQ}2uzXj$@pE)5g_DRm(bB}Jmk=k0cJG6UFL~UR9`fsy#Z7=*>w{7c+x|t~)V5#c(*Jw#Qs&=$)ytc&RhTE;ToJfvNr}49d8H*==9{*r zzuN!x|E#a)Z@<0vh;Nr&&&NHJBwW5szN~Y3CTHBWKT0yiQx+r(9OIh5TzkDw^mfr} z_Lcvp{L&AU`y;Z)Bb{rJ;o95_C%5JvHveknqO^y1(hhC8^SKr3UA^#?e6S&;I)!^Pg(f3p#%Kc|X*{@cd#|(a*mW4JX%e zzStV-;jwAkv45Wgea?RnGuBhKkSV<$^lGbdTyA~&CZp$xMsR|c4g6*B_9`d$R&Jz=F{GOQrGWT zQTU^%Z2iYc{0DU&$mMRj@l{m+t*JqM73boA$C-Cs4GU!594sKet3q2uH<91t_T|}P z)*F7Un`Qmsebk@TtEJNIGj^x{$-l1meWJYCO{2NC{;vbk>S6i3IU9afv zZ;5*IIO6ufQ09ci?fw!m6+oF`~3bxN~wxzF8eHX@Tcr9|vk2(&XCxL(01~2{nasSkbb37y? zpZ-w&UzB$wA};lQD!&=ay&~b>*$rv3*>`L!-0$-RzOcZ$r+f_ddDF5N`Tj{#0*gY>B9Cxv+Lo)!C?fd_2$93Z*{xn{^w1y0d=k zefA?C^xPH%we3w7jOK5BwKm+kvT@zE%#ADgq|+FuCZ?ypNp(G)ToPI8?YZT!>j#_c z4)KqnOwo4&Zfwm|eU|JT-n%Kidc*d(-`S}ZE2fz0p6+zp*<*Z?al_om>`47zmKDkg zUp@cYE&G|j`O6oh8=uTh^W6+nzEPtV{OxMiv?(F;`i||LGe=r5d#Cpq#=2|uw^R4* z+tw)<^65`_=dbuhLWc`=z1t4WWW4b!TGM;`4_1ju_p?*(D4kek;TFbQdE>vt&s)JS zeA6<&r%v^J{JoIv>Hei}_1iaCS-(5|{==W}wQ3uV+Ru7B-%a>!?`l5Z3Fd`wbKb7s zc}eN9$-h^3PrurFT&JMUt8DJ#ZLSA%B!s1K7FxW z5p`$I8{Z1=&aR%irR<8)l5JOYSCy?S4!f3p`kA21e!al#qTV9OSG`AkK23WraMt-| zcA1xvh`0RIioG&M4x3#y&aSO@n2{c~vRjU^b4|$W?@=?YUtD)S&a3R7q*j&L|EFyK zmH#iK{ofzCD&=nff3i(iZQpy2PjB)ApDnV^H9S}FdGmTp(^ScRRsY;CLcc#Mbf@pw zBGmJ(!L={dNJHt~t0MvKe)E2xx^VvH>!jR*PT8rG_3Jmw*-bz9>2t=#8&lj|qW%}` z5Q=|ODZ6$T-^&jNLbvosD*iDQOxebJ)o4|k|M}Nz{y)0D>{{K)JDI6f8B+wND!yM+ z8*6^_alw-C?D>vs>K3VPu-GrTmEG@e`MqN|O25y|l>C3ZI^guA*2*hlKjWC6yvptA zOI2XnH7WMe%!c_-1Yf;hTzK}SX!8Ci%?B>=oxb^T|MhoODPK42c=qG|?U_p_obt5H zzu5MSV?pGvO?f7#z0dyAUtQ?FnqP6Yey4GeeDK=i|CIu#z75)OOjomV!1u$(BktP+l!_-JL>-k zOZSS+an@bOZn2Xo($2&vV@3VF{Zo<>uX|-3{4mj3yLMW~wYG|yT(jbh%j2SMSN&PP zv^z3&+ViH0zvtU!PfuLZADpv7^fcSo_T0FoMavBr?|yRS2LFwfm6x;lXUv+~eNXNC zuKjzQ53?~(I`~53Sf_pe$8VREh3dZMWIW95zqT{ZxN~AqX1&qeO}pkfD;t(EZSDW* z2N^2y;{SH`LSyCgrFOqEY9pR4?o8diBXDz^m+AJ*k7o7pw^!HSxB0drRc6B63bpL7 z>#tOAR&{)w{_1SSTe0JdfAQw}`t3b)%!><#l%sFiWMjTr4^l#;%>cm79y6?#x_rr`Vcn`u{sh^{U3c z$!uZToUhhPuA4b`@w04Q?`XL#kw5!?WUh8Td8691jK^Z>9i7yIz0V`>Ey*;|tDI~S z_J3oH_p_OE{n@m#s#Sud*Up$?eCK6F<*MaHmjtfv{&p#7%I!%;&sDdbyUoDuHtp}0 zSk28(mu!iPKe=G*_NB85w?v%ZaxbJqe%Z02#c#is{V=(3@79Jl7b1NAUb^ymZK{6X z+xnH26Qy4StW-X4^8d~gADjJe?EJG<{Fm(b(iECE`LDn3`n~cSw%m5M%33U5|7Lf8 z+o9W>*{@1U4X@t5^QSdmq&LI&;fDS&tG*o5JteGm0&*Qq;HRmas9#mCbnlQb#uXi>N@07pCZvD8- z&{6KXG)3?ED_6}=8b%S<&NfWfsE)n4-LyZj>dl{=V;Lo@*0wF(bnMLj_^=Yq=_}?0 zXs6HQ{}VNL*8Nj`&4tQO8qqN|M8!ZI#S)(gjXC0A+)d{5Z6^8B-@h6dr~GjfCfuY6wnC2pGgwe@e8 zd|S9Qd(*}_Qv}bw{IUO8@Bb~U{!c2r@syz|?a%s)$u6%~2Wk0fKmNavTjO!PbnLWc zp?lQaI5XnpYyZrD{@`nr&57vO$1b^Ct=o`#SJqYXbbN+f)}2jH@2~CepZIv^$9l70 zTbWn#3x96(Fk`-H^K0IsU0+{c@VdWfZCSzD-HnNV-sk2$yZiFT{nNW|{n&r9Ds%dY z*@+jf-_q*-Vsd`glOOS_YHuRvzIfUFG-1}1+ss=}txT2Az4N!=hQ;YaQIDp*+;}=* zf4_~;$#Ulb_4ckkbg z^9$bC91mRjx?gbK`@L@twYT`5y8K`0Y~RCd+l+Ucrye*}u~_%w%-4AxuZ||>E-{#Y zI57Fn4Q1J-Cd^zXdcLbInfe>R(!Bc`~;5*OdCL_lmBwUAVRK zp;Ogyvn|%Eui1A6?r)7YGRTwMt5mUN4U6IDC6DeDr9Tx-+Pr)E0gr7Kt1~uw#6}>1NY? zrq6m9*%qBUA*(R^VBXAIn>HUvB^Oc4@%x9{Xs&Bi3iC-s)~&^ZE0ssXMcuPdePV z#xv}Y$*bil21fBK4d0xq+Q*f5W&3yi`|_J#Z%(sIGu&3R^w-muOEph*v*)=y`smOf zT$Qc8e5un?8;-AY&YRtQe$DI8u6VBh+tbVBcjz`AUh#ZqPPfO-SGvc`)*d|~_J8U* z$p_1)UoRH_{o?UvwR>(}n*Z-Tx%Oc16s_A!Qjf2z%T;B1?;Ex^lT+;Y`puC#PuKEh zeoJ=Ej`zB?XZ_=dpi__oGNd8*3P1~in%2ZsR{d4Z~1zT%%_-(89eKm76(m(#TDo{V%e$(PG3G1+K zcK3Oyw%n@rI|^@D)dx4fe;hVZ{4D$brH3-ansY?`;`ZAx-00M=fBe2+rFzoc5Y2L- z+-mK=i|0-_HesE)=C|ipf7okHd!8b;v{b77Q*{vACg#_bI=NF%Ec~}RrE{}l!Oz+M z|9vSqyKer|oPEs)Z`qv{+k1Vrv2w%Wt7#J-$~kA>uKc9byRYiZ>YIN11tH@jzjp8c zeQ^4>-0p*GzOveN^q+G{o?x@@q4uue-;qUOoi})=^|qY~PPpA)YG=pOZL&q?#1y-* z)7L*0-=BZwV5#inZl3$61RhAVMcR7JYj%^3zkF(k36rpx>17Ka9?hIN(vm{Id-qJ( zl{qhC^3@sjM=vikoMUBsI#o7-``7bkM){x9AMSE@j9NXt_Ql&=kIi!;Sj_%R`rbVC zVk)22scp&sPQNN~srk11OyI_%I6H-NvlDw~&x>ikEwqv4%A?ZC_*u#K9_pXvj@C}M zsoxd8#7l+U)$-gI?mO%AJKy(}GcRrU_3)JC^#|dfH46XkT(Y0dTFF~izNB)0@qh1Q zMJ8rFyBXFilB)he)~0F zb;GvyNs22cv7P*5HT}d2vqz~;?YpO(2-CLwwyMtb%Bhm>-x+JSKelXMnHF&R)6%7u z6F$alox+pdajo=vuypZ;J$tQl*S!5=``zYM*%YJAhFYa}7_VD<-1Xd&Ewuf0nPy+* zbaC;!r?Wp#4$R-Osd}dN|G>@v+%uM3sXraM*8aKV+E=k*w|rKFTIt??zsbLY=UZ}B zc6__&qU4a%!jG?Cy&S$iLgkqLlDP?NY_FKl?UR3pmDNZ99uug`;D^F`6;v{w^ZKr z{u_a_Qtxh@{`6Xi{iDvxE6E4{U8~o%Z7x5%l_fGf_|<&&+)sDo_x*7WiL&3Fnk>t8 zIL|X>k8;M(4`*NO_745HbE)?pgHQgyuKeHk?`Pq!Qx9gjbkDl&RquY_)5PUB&wO#7 zo*J}9cAf8b*7u7-Zdh|4`?x=1@{Myn|6i9*yA@aQt|B<{*#B>vGgfZCeRhIPdq(w{MxJce;>xwN4$7kzkZ$F zy?(VNJ^wc+ywJLSYv=sgTi+@@`nqcBlan*s{UiNPTlXIMWNyc;{H`qQ@r2lY5AW*F zt^cxt^_uFv`?DnHJ^mjnn^!e!k*xOBM>jtE>F^&f)_>V^#9eVt{O9k-zez)zFNfcX z-}hbngXi{k43+5H!yU&{I~7QDrLIoI^U*?LoUuTmC; zuiKW`Tk1@FSdQon`roNw@|=# z>37BMUt`y@=}xSbo|1wDRnudTwl!l=HqiM(@kL{NBarLz$6-)TLF1Oskzm zKQ=TS={VTLSh!i_=H%1MPpmSzaXNQS=yZk;CAW^rEzJ(PER(-|3%|hI_(xA~95bBf zCLjGa>5AIdbqCwGef^SsZbeFLR&ByAuMlg_hAFr2+-c`|uM?mf+%SFi*05{ezTP-0 zkh!UTO~vorbDuuO?oMNV{PBp2QPkt`Nmo<%7|je9IvKTb_L?w%{a5wU*Mnk0>$hrU z6f(}vz49j~`>(yacguAK`8e-8o7}2?&25~g;(9FY_~(t+>i6$FDU-4DET?t4Ze`%T zW0&IP%?~bJmu<5D-zB?Q+s#5AyB+uz#N<5hnj-JN-HOYeiz@ivG5dH+Sy0$Q_lH*C z%r@ak9`Rx)E}29kBFs!Z!U&x7y^d;doK(?)8hmH9NNk9N*JvwzAUR zFy_Px!LN5YCo-qn*G*f?>$~mLg}S3R-K0b6w-seAefVPS>Zwmx{J&N-ea=~?w9@mp z=g<2Q>t@w%5tOg&^))Z~*xXJEwhZ z)4{ywk0;;xqvAc=g(b*{ZNsd$x%~UQn6j3xoGI|uuPxP2J910Fa?hx@R?4+ea^ig- zn+y4qE5DZT`%9?2+Rv_j{cHVm)BH6h^R|Z_$(eI~KDXRf-fT_l{;M);nWys{h&Zq@ zGXAN0g6U18ty9a6MOj*J7W;2@^4nqW)oFRWqFeq=IedYG|JNIb_l=9~I^%B#{ZEbk znmd2mEGy-^L88&m1UC1kp6v^nrTVet%ch$um#40rGVSJT{f$r6Yu0Sn%8$E{z3RxV zhHKLqI}#V9&3gT_O5ncH#pqYJ_$wb=pB^N6{QqCB?Q`zVets+L@&C(d3+7kyKK;(q zUAJrMwtqgcA6cGx9{v2mY|nw_wneFb;(t$>qh5uY1@1O}`h;eerxzW#6uvA8Y^W+UYNNdh2WY z@&9$YOKhH>{5Obe0@jKVb6%W^2h$0t+=jO@9Nd8Z&V|( zZ2o%t4V&0ye9wK^7^m=?sztadBOM2cuw0nX|nTf z>nH6e*6;uQBwmhXhZD=G!ma-f-v9q#@=C$~?_T(?nC&4uk$*e0*^UphHTJvfe7|z= zak5np+o|Yd(L47C-#2hS`1-Ht>1$DWi%L6gRD8d8%{t>|diDKfhZ}CcU-G-wE$lbX zCQr8h+f^y^1(%xjZH#(%oIOLyE@@>shw6c+l~>QrtM4_~a@C08+vaKW|E69_>fQIL zWdG0mk5W{Rm2C{ml{;Vdw4B4xL$qIcO_20ShVej9kbqZG0Wk{aa zWh+pBd@qsNIzTttcZt{`xr$HRS*@QkoagM=HEqRJ!K=rUzrDU%+y9G4AU3rxR_u1% z(jzQ?jvYK*d|G76Q!}r9R}^De61|v?20i;Zv-*mm(k`iO*BMLWtgcqx&6VZ1-B<9J z`|Ip^ReC$^C7I`?)<2ze?scbZw)-TpegEG*eOb1STPh-teYwQtLuKkKSayZ_4b$dT>)etujL_#<>tzS>^UY=PGl$H>LD`t(HiL zur~d3_uqxKCC6n;a$B~_thC?M@uYHYSN-{K|L>jmxN@;(c}MAEb^G5F7q9(%ecI=B z;ZAM8@}K@#vAnm{yu|wBwgpoacDygh5dQTbRYxjv+vyFe-Iq78gk*N~@tUS{fsL-G1UzjVf})hK?o;VfchId!NiEy)?WVHpuc);tXXE1Q z71usnl78H9Uf7na^Ruj9=T0*Z*%fo4=C0xQ%U%pRe9vod8weho{$1nr8;`i)|1+AR zR?oVk`Z#Ru1~+l7sP(H)tg5|!#y|4cWR5jYnb(xQegFGT@8kb(od1-6z4a#RUSMc{*(nV{I{a<@dV_MFfoUmNY@49ZYpFYoE*wXVqccu8p z4bKePGG``z4O_7_Bfli};2OS)zFVfJd$t!v^vOT|zv6%0&0oLHzJ6*oZBfmX#JOKL zrc5ik?h+EVe6b-@$Cew9A52>tpZRl1&wo{~_0zhfUVgjzR%zyLt;4%jjLL7>KCWNA z+N>+^f9U7cs@Kf)7JhoO{Lx%hqi5b*p3jT_+NFCvI`s650*U{>Uqo%1vg)P zBN-m7>YZ>xK!{mE#f3va(YQgf;p7R9lLm^CXBwvTNHRz=Ir_Yqz!0hC%rXDbo2y^# zS5?o=?!NHP?&kM5Utg^&{~LO@`fdIH+53MTyzcrpJ|$q=I@U`Y7f2R|-3jPkv9(X( zM^*Z<(>rI}Iry{g=hp>l-}gq`T`wy>^Y)g~wo}FTZy6T-73zL`aoY3OJYL_VUth51 zIGLVRtnhxy&FHR;i84RsD*cb~{Yg90d;DF7{(i%xRreI{tl;gQakZa!o#DFp^{;>5 znb{t7Aa4DYCM%~8Hy_RMIlQj->Y={Z_mva+()Eq=7j{N$XxbdxR5)v|&py?qeS6Fk zqFN?aEB>~rZ57m<^YPkkd1sq%p|=)CzJ2v;=Uay3hSArmjf#^C!fy4=?YVk*=S}C+ zd$@I(&%IvvcAMC}`|3ORtFAui>Zl9%Pc7V*;`Z$v(}^ozRsC8fEMB{7-SslVu>9Ne z-!8v1v-`eP$FVzAo_`Kie*3R8FS^q8%KW#_GWag`^{qK0<-E@PY*f+LOEWj#{&{Q8 ztd9n#D|%v}9FPK|QAy`tyWz2x(9=8vuz&fDjua9L{h z@7xVDHgX5D7UxuKJ^Sp1dSF}jm0UgT{;O|zKmV|N=M+=gVfbuw>DoIc^S91g<&%DB z^@8Isp1*XR%P#Z2ZCO=a*u>-3WxIb_gsW-)+y42|@ttNNy~$Fyo1OKa&3jQ9d-v`B zo0FbS%AQ|Z$DXnD>93G0H;2BI(Q)O1vc(54u35cx z`@YHRd$;9ZFy|?+`<#8`*%{tRi)+GWU->@g#wBC->er@gd*-!johf}YWt{|n|H2m% zpU!PG+*N<&>Y5^n&l0y6%dT16aXf13^Bn)O; zl<#eIOJ|kseyNwAKTa>LI~#lDw(0qh_&Ha7vUOIS*wv;UQ6O0?aMUp(IS^+b97o@cp7_U)|??b!4y;>!1zn^LbG zJEhCiX};Cwtk(L~)^DEdF)J^-v!~4V>DE27J}Rs4m3_Bt)?DN2XHv)O-(^Z&EdF$M zvuMrjo>dPQUMh_k=SZYWBt;9|35$8V?E3L+1u!k|8HbkbT3=G{&vcZ z%f_!CxjeIu`X`s3{pqH-anzD~*>(T(4nP0>?dZ?0_|Hj4vJ8J#ZhU?3QIb;C*V!{S z=6S!2^v}K4CHzEw*WB92*3-JKFW6cn6TMNmZd!<|%i4y`Yq$LPFO!_DwXQoz`|_r| zkM$|FSASN?@07aQzyJSY`$BU|``vYk2hMMh|95-;pUdn2Tzg;B_kF+k`L};>%&EvK zvwilt?rhzWOGWt(XUo<|R^PU6ICuZ!?9G224<)bb3Vq6Fdd%W{%^Du9d-A5T$5ZV4 zD?f|^ko#|6o&%3KV+5O(9hknmb%+NcPGGEQ?_ooS)7j4=rSiUs3U1Iaoj~=0{ zvB%f$TP*+Y&yk4-drsaeO5b|v$V)L zRLTB7nK$W(+p(PWp;n81dqQVl2t9ZH%(t3(%j2vW&a=gK-ugXZ^{wX?j}Og`4h-?O zot5dG<$Y7{eB@hWtD=04>H`t4ABXL;72UaD1#jEUNz=D$^lqLJR(f<}mD#%UJyM&> zcAkj|K2!JXqV-X|kH>!$o4sFg`tH55&@F#bXID+WZ&$aK^?J|l{l$%8owL{SpM8<>jwG?$>z`XZHAwdbs2q)3V%#Yx1jN-a5T` zV>y4VynJz3ujc!6b<=`mbHnbgdH>??=JZv)4%^SXHGC4cU-|gupLsu4=>`1E_`10- za#7pUJHA$Z#l5N8(|#yFoA~0#)m8Vt{x5u%b4+3DXWMA6wCs(4|11`gSRB>sX?emW zYW?@nn_m>wzNdXVaCN`Y(q}uv=A7RaKL5R|%vO=#VwQbpZ$H1?TzTcS-qCyE&*yx$ zTi~Mlp7(gh*0oNnE5m*(szYY}(Nf5fHk zFt>HzU2hY8?6{5cgzn`9@A}vC zWeVQb4PAWw@6A20R=cdq{o?!LF7G+XFB-dK6x_Bh(7tRcaJEWy+4Y?E`*Z%D_mN3X zo0e65Kf?XDr1J4)*YY;oZ*42+sl6|8UhCie+8TM)tZZ5F9<7Omtk%E(_w~Bhr25MD zrj@pqKdt??@%Im7qfkR1H@h(T|NDBr{{8>w-u-`18|EjPo%%WR`{DY(&+GqOz5nO! z|6f-7{=d84zF#CUjk~g#IqfRj<$c{*UnUe?<4SuPTA~)bUkw7t4jq7`{5i+qz@&B6fD;!{5X<);{~aSa;g3YGVV5<0^Z; zYiq?=e7bXK^YYL8IPJe3vAcgKZo9$`gQDEy}shlY1@2f+&Zv3uXUbi z&~|~+d8I$Nj+aG82u8X(_D{QTyZPoRZSH*gzToG!wt8adCy|Q zbRnY^>v`A6-FR2Cr|wS%Z{e5!$C+~FvVUJ}I%VGdx>{Q*pXr`qcJs2S)$x6H_QK*Z zQPpSPo2(Nk5kEU;ujl#Or#9>Pr2Ie4xL}&a+NNX4i+41AnYZ`+_S!4?Rw2gozOxzj zH(0-0Q@3r_8~Lg04YPz3?d$jdGI!JEICd`Oj-c`LH!rP(zMOq}>CNM-YiGY_{1ld# zdvo6Dg@LV8Yl~zbf6SUL|Lo1q{Pr_?`))Cq|6-kKJ8w_i>5ZB1uB_WOXYIZlzrA^j zU(3{&pUR${wUu|XozLF)!j^Gs@A*Fes{3%Y?Y->X*A-tc@;b97aH;Vx7d4Al)oV|k zzcYV!dQ{&R7wMlir`@;qP32wpbp6+V=I{QNsek`h;^VP?(TrTTSC31oE!=yzu6^Bi z+wImrkCNAKmV7^uc-8fU#$$`neBtjsA-3mV^goWhR<*vWWR{d`_2x|DACWB2|HN;0 ziMzAoU%}VKW_=Y(``c>P?wJw4JZka0%%3}+X1dLLyz_Pc(ygD)?6W<#k#VQ=!_`Wg z+TS%4uClr>K8ldXUAO)Bu%z7E^I8&7T=kuc>;tGwHGNlrCp>D0gv zUyJy9a+SBZ?UB&B_PYOc>SCEtSL^+McSg&{*lOATqkehG^DRj|wr^ygpK99wb>iy4TI+xF zBeQ_Zqss-DR$ z%og4^>(FDhNs)%{zpfNxcT0TVcI(l~WMM`*WCV7Z!4aw zc&w>Z?Al&m7t1$>8@?Yr5!7?!H;;1GyI0GvOGtl>S{bQ3f3s@!8L{(6awb+r_y3Zv zeIsF-mU7?b(f^BCg+1>4yJqf>1tK|Ri$TMCaF6u>B zpIwmo<-Xae|MO;F8D zU*2dhBe>|zi_MQVM>_hq)V^)~HnX;4PupE_?XB;N-pt-|WXpBwD%e8lug|C|K|-4ySO>KW2yq< zJI_RD-xGcK@ber=gE{3Ti|M;0{r=mr{e^Sl{PyNvTlmwn7c?cZ;5zL@vH#R+-s^~L8j zR&V}&{@VZgPlmsKzL&JJI#@CLYx0zsG9ygo($!5KIOULM{6UuYHzvKy60mWOGU8Y)b?wgMz&Yo zTM? zwv&7uX}znk77RuZu?$k`#SgDsm#6a|3ALLv+kXR`+c!>$!o&cZRH>DnXE5l z6@5lfTIS}h&wCA9ukElkI+`1tC7$AEVCdR2uQB@H{?l(fZSA&AzHsclnRxBL@1?zo zYpT6-HlOkPn%9?n_td`J1zVKP@~*4>CsBN!BO$JS+VjfZjq>|nE&e*w>U;XpHMi$p z&%K;)+q69NY4Q2PD}L>-^*vDYd7t6!r!%iVyYGJQcTwN$ncK}j{-14BEB$|aV43+e zpUYbV_uPB7-1a)x`&jw@?oRjqm+!68KFfI@G47xIwCz>h@iW$|ZU| zZ@*S`Z^%zfkY|iL`!vJFTK4zm^}pgbhhDyQ-1_(nt;fkHcG`XWx;B2(|Kkd^_dG7| zmA>$6&8N8^>ut*YW_~<2r#C#FXDf3``}@C}_eCw9`gBFWDz+bsbBzAwKXyD5y7ytK z(PF>+%HH|qmTT_0Ey__^ym90G!`tqbXHTw?*S~$qwrl3*r{!03CPvC!UH40V+a7)W zyvHY2zmyfsUz+;l$fn!3cTfAM_wRn?xtG>@ThjWap8weXd584>)lzYfpXS=VnlJtS z(f>&8S?8bc?~(n#{{0T=|7LwPfA8P_e<-H@kNm$1b$j(^4fBoXOFw%p{{Q>;{XHMq z%^YdgsshupX>-CDaIr8|rq1@^z7t0@cMZex#`}UXG-t4x&ozj8U zSskp0vW0cTA8*|$l70I3$E?Ng?kZJ>F0i=u%$0k?BA#a%<)O#t{VF|uO*G-HZ_~W1 z9tT6WJ?B!mw;``EW6r;A3j1y~P3 z_A&qAkI>TRN2hPSZ}wW^@4w}j*WPh6TfAmlSWaZ#>bdFrZl00+cl3+_`q?kDnP*?#cJpUv+!5_1LdztKP=!{3cqmbn(($ z+4c8trSzR&{p-w6X}zhpu77;@_}dQi``c~?%lKm7XQiAtjh<%OYES+85gK4-gQ7uoZF^WBMZKjkVLmESMBC+=4k zSbHY<^5*S*+cy5pSiU!``scSD%L)*k^TZ-I6`kHFL`+^{?7) z_pEQlyBfP&S4-E##w>nz;aA}rJEnW9%3Oc0xw$W@AU%7YIE#C?r(OTI)UUsC+TV(& zrAa^9Z1-&4ocT)s=CAeq&X{m7=*p)G+xy2S6|Xp1n6uV+?R@W(`r6Oi&BS^yuC5DN zd+f!f`@5enjBQ)XdpCIV^3{v;-+WpY$Nwkx1^?Y|zUgE0djEe9UI+jGVE=gk|6lI+fA5y(WuO(1pq0U+ f=29F2|MUN|_Z)oiV8bnWBamU9u6{1-oD!M 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 QdJQtl)78&qol`;+0FP$w1^@s6 diff --git a/README.md b/README.md index a51f9c53..b9726864 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,8 @@ -![logo](.github/logo.png) + + + + logo + Useful tools for developer and people working in IT. [Have a look !](https://it-tools.tech). From f5c4ab19bc10ea468a453a1460b1de2d7ccab87b Mon Sep 17 00:00:00 2001 From: sharevb Date: Fri, 20 Sep 2024 20:39:40 +0200 Subject: [PATCH 3/5] feat(new tool): Regex Tester (and Cheatsheet) (#1030) * feat(new tool): Regex Tester Fix https://github.com/CorentinTh/it-tools/issues/1007, https://github.com/CorentinTh/it-tools/issues/991, https://github.com/CorentinTh/it-tools/issues/936, https://github.com/CorentinTh/it-tools/issues/761, https://github.com/CorentinTh/it-tools/issues/649 https://github.com/CorentinTh/it-tools/issues/644, https://github.com/CorentinTh/it-tools/issues/554 https://github.com/CorentinTh/it-tools/issues/308 * fix: refactor to service + add regex diagram + ui enhancements * fix: update queryParams * fix: deps * fix: svg style bug in @regexper/render @regexper/render use a stylesheet in svg that cause bugs in whole site. So add regexper in a shadow root * feat(new tool): added Regex Cheatsheet * Update src/tools/regex-memo/index.ts * Update src/tools/regex-tester/index.ts --------- Co-authored-by: Corentin THOMASSET --- components.d.ts | 15 +- package.json | 5 +- pnpm-lock.yaml | 46 +++++ src/composable/queryParams.ts | 33 ++- src/composable/validation.ts | 19 +- src/main.ts | 2 + src/tools/index.ts | 4 + src/tools/regex-memo/index.ts | 12 ++ src/tools/regex-memo/regex-memo.content.md | 121 +++++++++++ src/tools/regex-memo/regex-memo.vue | 32 +++ src/tools/regex-tester/index.ts | 12 ++ .../regex-tester/regex-tester.service.test.ts | 106 ++++++++++ .../regex-tester/regex-tester.service.ts | 61 ++++++ src/tools/regex-tester/regex-tester.vue | 193 ++++++++++++++++++ 14 files changed, 650 insertions(+), 11 deletions(-) create mode 100644 src/tools/regex-memo/index.ts create mode 100644 src/tools/regex-memo/regex-memo.content.md create mode 100644 src/tools/regex-memo/regex-memo.vue create mode 100644 src/tools/regex-tester/index.ts create mode 100644 src/tools/regex-tester/regex-tester.service.test.ts create mode 100644 src/tools/regex-tester/regex-tester.service.ts create mode 100644 src/tools/regex-tester/regex-tester.vue diff --git a/components.d.ts b/components.d.ts index 8e59366a..3e65c3cc 100644 --- a/components.d.ts +++ b/components.d.ts @@ -130,23 +130,19 @@ declare module '@vue/runtime-core' { MetaTagGenerator: typeof import('./src/tools/meta-tag-generator/meta-tag-generator.vue')['default'] MimeTypes: typeof import('./src/tools/mime-types/mime-types.vue')['default'] NavbarButtons: typeof import('./src/components/NavbarButtons.vue')['default'] - NButton: typeof import('naive-ui')['NButton'] - NCode: typeof import('naive-ui')['NCode'] + NCheckbox: typeof import('naive-ui')['NCheckbox'] NCollapseTransition: typeof import('naive-ui')['NCollapseTransition'] NConfigProvider: typeof import('naive-ui')['NConfigProvider'] + NDivider: typeof import('naive-ui')['NDivider'] NEllipsis: typeof import('naive-ui')['NEllipsis'] - NForm: typeof import('naive-ui')['NForm'] - NFormItem: typeof import('naive-ui')['NFormItem'] NH1: typeof import('naive-ui')['NH1'] NH3: typeof import('naive-ui')['NH3'] NIcon: typeof import('naive-ui')['NIcon'] - NInputNumber: typeof import('naive-ui')['NInputNumber'] NLayout: typeof import('naive-ui')['NLayout'] NLayoutSider: typeof import('naive-ui')['NLayoutSider'] NMenu: typeof import('naive-ui')['NMenu'] - NScrollbar: typeof import('naive-ui')['NScrollbar'] - NSlider: typeof import('naive-ui')['NSlider'] - NSwitch: typeof import('naive-ui')['NSwitch'] + NSpace: typeof import('naive-ui')['NSpace'] + NTable: typeof import('naive-ui')['NTable'] NumeronymGenerator: typeof import('./src/tools/numeronym-generator/numeronym-generator.vue')['default'] OtpCodeGeneratorAndValidator: typeof import('./src/tools/otp-code-generator-and-validator/otp-code-generator-and-validator.vue')['default'] PasswordStrengthAnalyser: typeof import('./src/tools/password-strength-analyser/password-strength-analyser.vue')['default'] @@ -156,6 +152,9 @@ declare module '@vue/runtime-core' { PhoneParserAndFormatter: typeof import('./src/tools/phone-parser-and-formatter/phone-parser-and-formatter.vue')['default'] QrCodeGenerator: typeof import('./src/tools/qr-code-generator/qr-code-generator.vue')['default'] RandomPortGenerator: typeof import('./src/tools/random-port-generator/random-port-generator.vue')['default'] + RegexMemo: typeof import('./src/tools/regex-memo/regex-memo.vue')['default'] + 'RegexMemo.content': typeof import('./src/tools/regex-memo/regex-memo.content.md')['default'] + RegexTester: typeof import('./src/tools/regex-tester/regex-tester.vue')['default'] ResultRow: typeof import('./src/tools/ipv4-range-expander/result-row.vue')['default'] RomanNumeralConverter: typeof import('./src/tools/roman-numeral-converter/roman-numeral-converter.vue')['default'] RouterLink: typeof import('vue-router')['RouterLink'] diff --git a/package.json b/package.json index 63e5856a..f5dedc0c 100644 --- a/package.json +++ b/package.json @@ -37,12 +37,13 @@ "dependencies": { "@it-tools/bip39": "^0.0.4", "@it-tools/oggen": "^1.3.0", + "@regexper/render": "^1.0.0", "@sindresorhus/slugify": "^2.2.1", "@tiptap/pm": "2.1.6", "@tiptap/starter-kit": "2.1.6", "@tiptap/vue-3": "2.0.3", - "@types/markdown-it": "^13.0.7", "@types/figlet": "^1.5.8", + "@types/markdown-it": "^13.0.7", "@vicons/material": "^0.12.0", "@vicons/tabler": "^0.12.0", "@vueuse/core": "^10.3.0", @@ -84,6 +85,7 @@ "pinia": "^2.0.34", "plausible-tracker": "^0.3.8", "qrcode": "^1.5.1", + "randexp": "^0.5.3", "sql-formatter": "^13.0.0", "ua-parser-js": "^1.0.35", "ulid": "^2.3.0", @@ -93,6 +95,7 @@ "vue": "^3.3.4", "vue-i18n": "^9.9.1", "vue-router": "^4.1.6", + "vue-shadow-dom": "^4.2.0", "vue-tsc": "^1.8.1", "xml-formatter": "^3.3.2", "xml-js": "^1.6.11", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 2311f3af..e43a3217 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -11,6 +11,9 @@ dependencies: '@it-tools/oggen': specifier: ^1.3.0 version: 1.3.0 + '@regexper/render': + specifier: ^1.0.0 + version: 1.0.0 '@sindresorhus/slugify': specifier: ^2.2.1 version: 2.2.1 @@ -152,6 +155,9 @@ dependencies: qrcode: specifier: ^1.5.1 version: 1.5.1 + randexp: + specifier: ^0.5.3 + version: 0.5.3 sql-formatter: specifier: ^13.0.0 version: 13.0.0 @@ -179,6 +185,9 @@ dependencies: vue-router: specifier: ^4.1.6 version: 4.1.6(vue@3.3.4) + vue-shadow-dom: + specifier: ^4.2.0 + version: 4.2.0 vue-tsc: specifier: ^1.8.1 version: 1.8.1(typescript@5.2.2) @@ -2480,6 +2489,17 @@ packages: resolution: {integrity: sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A==} dev: false + /@regexper/parser@1.0.0: + resolution: {integrity: sha512-S8AWIGpCNdl9PNHdbhI6TpXZsPk6FDU/RTZI+6UFF4rVFqDQKjCIbZSgFu7NihoEZKq57wKFPbbT1EzrjVvPHA==} + dev: false + + /@regexper/render@1.0.0: + resolution: {integrity: sha512-xYm9RUgnhhZotTtf8UZpK1PG2CcTRXQ3JPwfTlYUZsy2J+UcTVc7BaO/MJadpMoVuT8jrIyptH4Y0HLzqhI3hQ==} + dependencies: + '@regexper/parser': 1.0.0 + '@svgdotjs/svg.js': 3.2.4 + dev: false + /@remirror/core-constants@2.0.1: resolution: {integrity: sha512-ZR4aihtnnT9lMbhh5DEbsriJRlukRXmLZe7HmM+6ufJNNUDoazc75UX26xbgQlNUqgAqMcUdGFAnPc1JwgAdLQ==} dependencies: @@ -2629,6 +2649,10 @@ packages: string.prototype.matchall: 4.0.10 dev: true + /@svgdotjs/svg.js@3.2.4: + resolution: {integrity: sha512-BjJ/7vWNowlX3Z8O4ywT58DqbNRyYlkk6Yz/D13aB7hGmfQTvGX4Tkgtm/ApYlu9M7lCQi15xUEidqMUmdMYwg==} + dev: false + /@tiptap/core@2.1.12(@tiptap/pm@2.1.6): resolution: {integrity: sha512-ZGc3xrBJA9KY8kln5AYTj8y+GDrKxi7u95xIl2eccrqTY5CQeRu6HRNM1yT4mAjuSaG9jmazyjGRlQuhyxCKxQ==} peerDependencies: @@ -4962,6 +4986,11 @@ packages: tslib: 2.5.0 dev: false + /drange@1.1.1: + resolution: {integrity: sha512-pYxfDYpued//QpnLIm4Avk7rsNtAtQkUES2cwAYSvD/wd2pKD71gN2Ebj3e7klzXwjocvE8c5vx/1fxwpqmSxA==} + engines: {node: '>=4'} + dev: false + /duplexer@0.1.2: resolution: {integrity: sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==} dev: true @@ -7758,6 +7787,14 @@ packages: ret: 0.1.15 dev: false + /randexp@0.5.3: + resolution: {integrity: sha512-U+5l2KrcMNOUPYvazA3h5ekF80FHTUG+87SEAmHZmolh1M+i/WyTCxVzmi+tidIa1tM4BSe8g2Y/D3loWDjj+w==} + engines: {node: '>=4'} + dependencies: + drange: 1.1.1 + ret: 0.2.2 + dev: false + /randombytes@2.1.0: resolution: {integrity: sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==} dependencies: @@ -7928,6 +7965,11 @@ packages: engines: {node: '>=0.12'} dev: false + /ret@0.2.2: + resolution: {integrity: sha512-M0b3YWQs7R3Z917WRQy1HHA7Ba7D8hvZg6UE5mLykJxQVE2ju0IXbGlaHPPlkY+WN7wFP+wUMXmBFA0aV6vYGQ==} + engines: {node: '>=4'} + dev: false + /reusify@1.0.4: resolution: {integrity: sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==} engines: {iojs: '>=1.0.0', node: '>=0.10.0'} @@ -9268,6 +9310,10 @@ packages: vue: 3.3.4 dev: false + /vue-shadow-dom@4.2.0: + resolution: {integrity: sha512-lguI064rT2HT/dxqSmXtz860KOvCq+W3nU1jMqroTmX3K1H46q22BMR4emh/Ld3ozy35XJKOaNGcr6mkJ/t/yg==} + dev: false + /vue-template-compiler@2.7.14: resolution: {integrity: sha512-zyA5Y3ArvVG0NacJDkkzJuPQDF8RFeRlzV2vLeSnhSpieO6LK2OVbdLPi5MPPs09Ii+gMO8nY4S3iKQxBxDmWQ==} dependencies: diff --git a/src/composable/queryParams.ts b/src/composable/queryParams.ts index 9699abbc..7cc8cc0d 100644 --- a/src/composable/queryParams.ts +++ b/src/composable/queryParams.ts @@ -1,7 +1,8 @@ import { useRouteQuery } from '@vueuse/router'; import { computed } from 'vue'; +import { useStorage } from '@vueuse/core'; -export { useQueryParam }; +export { useQueryParam, useQueryParamOrStorage }; const transformers = { number: { @@ -16,6 +17,12 @@ const transformers = { fromQuery: (value: string) => value.toLowerCase() === 'true', toQuery: (value: boolean) => (value ? 'true' : 'false'), }, + object: { + fromQuery: (value: string) => { + return JSON.parse(value); + }, + toQuery: (value: object) => JSON.stringify(value), + }, }; function useQueryParam({ name, defaultValue }: { name: string; defaultValue: T }) { @@ -33,3 +40,27 @@ function useQueryParam({ name, defaultValue }: { name: string; defaultValue: }, }); } + +function useQueryParamOrStorage({ name, storageName, defaultValue }: { name: string; storageName: string; defaultValue: T }) { + const type = typeof defaultValue; + const transformer = transformers[type as keyof typeof transformers] ?? transformers.string; + + const storageRef = useStorage(storageName, defaultValue); + const proxyDefaultValue = transformer.toQuery(defaultValue as never); + const proxy = useRouteQuery(name, proxyDefaultValue); + + const r = ref(defaultValue); + + watch(r, + (value) => { + proxy.value = transformer.toQuery(value as never); + storageRef.value = value as never; + }, + { deep: true }); + + r.value = (proxy.value && proxy.value !== proxyDefaultValue + ? transformer.fromQuery(proxy.value) as unknown as T + : storageRef.value as T) as never; + + return r; +} diff --git a/src/composable/validation.ts b/src/composable/validation.ts index 472ca4b2..33a6a7b2 100644 --- a/src/composable/validation.ts +++ b/src/composable/validation.ts @@ -3,9 +3,11 @@ import _ from 'lodash'; import { type Ref, reactive, watch } from 'vue'; type ValidatorReturnType = unknown; +type GetErrorMessageReturnType = string; export interface UseValidationRule { validator: (value: T) => ValidatorReturnType + getErrorMessage?: (value: T) => GetErrorMessageReturnType message: string } @@ -24,6 +26,15 @@ export function isFalsyOrHasThrown(cb: () => ValidatorReturnType): boolean { } } +export function getErrorMessageOrThrown(cb: () => GetErrorMessageReturnType): string { + try { + return cb() || ''; + } + catch (e: any) { + return e.toString(); + } +} + export interface ValidationAttrs { feedback: string validationStatus: string | undefined @@ -61,7 +72,13 @@ export function useValidation({ for (const rule of get(rules)) { if (isFalsyOrHasThrown(() => rule.validator(source.value))) { - state.message = rule.message; + if (rule.getErrorMessage) { + const getErrorMessage = rule.getErrorMessage; + state.message = rule.message.replace('{0}', getErrorMessageOrThrown(() => getErrorMessage(source.value))); + } + else { + state.message = rule.message; + } state.status = 'error'; } } diff --git a/src/main.ts b/src/main.ts index 36ba3b7f..19d28bf2 100644 --- a/src/main.ts +++ b/src/main.ts @@ -3,6 +3,7 @@ import { createPinia } from 'pinia'; import { createHead } from '@vueuse/head'; import { registerSW } from 'virtual:pwa-register'; +import shadow from 'vue-shadow-dom'; import { plausible } from './plugins/plausible.plugin'; import 'virtual:uno.css'; @@ -23,5 +24,6 @@ app.use(i18nPlugin); app.use(router); app.use(naive); app.use(plausible); +app.use(shadow); app.mount('#app'); diff --git a/src/tools/index.ts b/src/tools/index.ts index c9003fe8..388cfaf4 100644 --- a/src/tools/index.ts +++ b/src/tools/index.ts @@ -9,6 +9,8 @@ import { tool as textToUnicode } from './text-to-unicode'; import { tool as safelinkDecoder } from './safelink-decoder'; import { tool as xmlToJson } from './xml-to-json'; import { tool as jsonToXml } from './json-to-xml'; +import { tool as regexTester } from './regex-tester'; +import { tool as regexMemo } from './regex-memo'; import { tool as markdownToHtml } from './markdown-to-html'; import { tool as pdfSignatureChecker } from './pdf-signature-checker'; import { tool as numeronymGenerator } from './numeronym-generator'; @@ -156,6 +158,8 @@ export const toolsByCategory: ToolCategory[] = [ xmlFormatter, yamlViewer, emailNormalizer, + regexTester, + regexMemo, ], }, { diff --git a/src/tools/regex-memo/index.ts b/src/tools/regex-memo/index.ts new file mode 100644 index 00000000..f1f56489 --- /dev/null +++ b/src/tools/regex-memo/index.ts @@ -0,0 +1,12 @@ +import { BrandJavascript } from '@vicons/tabler'; +import { defineTool } from '../tool'; + +export const tool = defineTool({ + name: 'Regex cheatsheet', + path: '/regex-memo', + description: 'Javascript Regex/Regular Expression cheatsheet', + keywords: ['regex', 'regular', 'expression', 'javascript', 'memo', 'cheatsheet'], + component: () => import('./regex-memo.vue'), + icon: BrandJavascript, + createdAt: new Date('2024-09-20'), +}); diff --git a/src/tools/regex-memo/regex-memo.content.md b/src/tools/regex-memo/regex-memo.content.md new file mode 100644 index 00000000..0f779401 --- /dev/null +++ b/src/tools/regex-memo/regex-memo.content.md @@ -0,0 +1,121 @@ +### Normal characters + +Expression | Description +:--|:-- +`.` or `[^\n\r]` | any character *excluding* a newline or carriage return +`[A-Za-z]` | alphabet +`[a-z]` | lowercase alphabet +`[A-Z]` | uppercase alphabet +`\d` or `[0-9]` | digit +`\D` or `[^0-9]` | non-digit +`_` | underscore +`\w` or `[A-Za-z0-9_]` | alphabet, digit or underscore +`\W` or `[^A-Za-z0-9_]` | inverse of `\w` +`\S` | inverse of `\s` + +### Whitespace characters + +Expression | Description +:--|:-- +` ` | space +`\t` | tab +`\n` | newline +`\r` | carriage return +`\s` | space, tab, newline or carriage return + +### Character set + +Expression | Description +:--|:-- +`[xyz]` | either `x`, `y` or `z` +`[^xyz]` | neither `x`, `y` nor `z` +`[1-3]` | either `1`, `2` or `3` +`[^1-3]` | neither `1`, `2` nor `3` + +- Think of a character set as an `OR` operation on the single characters that are enclosed between the square brackets. +- Use `^` after the opening `[` to “negate” the character set. +- Within a character set, `.` means a literal period. + +### Characters that require escaping + +#### Outside a character set + +Expression | Description +:--|:-- +`\.` | period +`\^` | caret +`\$` | dollar sign +`\|` | pipe +`\\` | back slash +`\/` | forward slash +`\(` | opening bracket +`\)` | closing bracket +`\[` | opening square bracket +`\]` | closing square bracket +`\{` | opening curly bracket +`\}` | closing curly bracket + +#### Inside a character set + +Expression | Description +:--|:-- +`\\` | back slash +`\]` | closing square bracket + +- A `^` must be escaped only if it occurs immediately after the opening `[` of the character set. +- A `-` must be escaped only if it occurs between two alphabets or two digits. + +### Quantifiers + +Expression | Description +:--|:-- +`{2}` | exactly 2 +`{2,}` | at least 2 +`{2,7}` | at least 2 but no more than 7 +`*` | 0 or more +`+` | 1 or more +`?` | exactly 0 or 1 + +- The quantifier goes *after* the expression to be quantified. + +### Boundaries + +Expression | Description +:--|:-- +`^` | start of string +`$` | end of string +`\b` | word boundary + +- How word boundary matching works: + - At the beginning of the string if the first character is `\w`. + - Between two adjacent characters within the string, if the first character is `\w` and the second character is `\W`. + - At the end of the string if the last character is `\w`. + +### Matching + +Expression | Description +:--|:-- +`foo\|bar` | match either `foo` or `bar` +`foo(?=bar)` | match `foo` if it’s before `bar` +`foo(?!bar)` | match `foo` if it’s *not* before `bar` +`(?<=bar)foo` | match `foo` if it’s after `bar` +`(? +import { useThemeVars } from 'naive-ui'; +import Memo from './regex-memo.content.md'; + +const themeVars = useThemeVars(); + + + + + diff --git a/src/tools/regex-tester/index.ts b/src/tools/regex-tester/index.ts new file mode 100644 index 00000000..9cc542f0 --- /dev/null +++ b/src/tools/regex-tester/index.ts @@ -0,0 +1,12 @@ +import { Language } from '@vicons/tabler'; +import { defineTool } from '../tool'; + +export const tool = defineTool({ + name: 'Regex Tester', + path: '/regex-tester', + description: 'Regex Tester', + keywords: ['regex', 'tester', 'sample', 'expression'], + component: () => import('./regex-tester.vue'), + icon: Language, + createdAt: new Date('2024-09-20'), +}); diff --git a/src/tools/regex-tester/regex-tester.service.test.ts b/src/tools/regex-tester/regex-tester.service.test.ts new file mode 100644 index 00000000..bd4efbbc --- /dev/null +++ b/src/tools/regex-tester/regex-tester.service.test.ts @@ -0,0 +1,106 @@ +import { describe, expect, it } from 'vitest'; +import { matchRegex } from './regex-tester.service'; + +const regexesData = [ + { + regex: '', + text: '', + flags: '', + result: [], + }, + { + regex: '.*', + text: '', + flags: '', + result: [], + }, + { + regex: '', + text: 'aaa', + flags: '', + result: [], + }, + { + regex: 'a', + text: 'baaa', + flags: '', + result: [ + { + captures: [], + groups: [], + index: 1, + value: 'a', + }, + ], + }, + { + regex: '(.)(?r)', + text: 'azertyr', + flags: 'g', + result: [ + { + captures: [ + { + end: 3, + name: '1', + start: 2, + value: 'e', + }, + { + end: 4, + name: '2', + start: 3, + value: 'r', + }, + ], + groups: [ + { + end: 4, + name: 'g', + start: 3, + value: 'r', + }, + ], + index: 2, + value: 'er', + }, + { + captures: [ + { + end: 6, + name: '1', + start: 5, + value: 'y', + }, + { + end: 7, + name: '2', + start: 6, + value: 'r', + }, + ], + groups: [ + { + end: 7, + name: 'g', + start: 6, + value: 'r', + }, + ], + index: 5, + value: 'yr', + }, + ], + }, +]; + +describe('regex-tester', () => { + for (const reg of regexesData) { + const { regex, text, flags, result: expected_result } = reg; + it(`Should matchRegex("${regex}","${text}","${flags}") return correct result`, async () => { + const result = matchRegex(regex, text, `${flags}d`); + + expect(result).to.deep.equal(expected_result); + }); + } +}); diff --git a/src/tools/regex-tester/regex-tester.service.ts b/src/tools/regex-tester/regex-tester.service.ts new file mode 100644 index 00000000..ec8682c5 --- /dev/null +++ b/src/tools/regex-tester/regex-tester.service.ts @@ -0,0 +1,61 @@ +interface RegExpGroupIndices { + [name: string]: [number, number] +} +interface RegExpIndices extends Array<[number, number]> { + groups: RegExpGroupIndices +} +interface RegExpExecArrayWithIndices extends RegExpExecArray { + indices: RegExpIndices +} +interface GroupCapture { + name: string + value: string + start: number + end: number +}; + +export function matchRegex(regex: string, text: string, flags: string) { + // if (regex === '' || text === '') { + // return []; + // } + + let lastIndex = -1; + const re = new RegExp(regex, flags); + const results = []; + let match = re.exec(text) as RegExpExecArrayWithIndices; + while (match !== null) { + if (re.lastIndex === lastIndex || match[0] === '') { + break; + } + const indices = match.indices; + const captures: Array = []; + Object.entries(match).forEach(([captureName, captureValue]) => { + if (captureName !== '0' && captureName.match(/\d+/)) { + captures.push({ + name: captureName, + value: captureValue, + start: indices[Number(captureName)][0], + end: indices[Number(captureName)][1], + }); + } + }); + const groups: Array = []; + Object.entries(match.groups || {}).forEach(([groupName, groupValue]) => { + groups.push({ + name: groupName, + value: groupValue, + start: indices.groups[groupName][0], + end: indices.groups[groupName][1], + }); + }); + results.push({ + index: match.index, + value: match[0], + captures, + groups, + }); + lastIndex = re.lastIndex; + match = re.exec(text) as RegExpExecArrayWithIndices; + } + return results; +} diff --git a/src/tools/regex-tester/regex-tester.vue b/src/tools/regex-tester/regex-tester.vue new file mode 100644 index 00000000..a1fa7958 --- /dev/null +++ b/src/tools/regex-tester/regex-tester.vue @@ -0,0 +1,193 @@ + + + From 72517002f39d5c5ab21d8473c2fcc04f12818069 Mon Sep 17 00:00:00 2001 From: Corentin Thomasset Date: Fri, 27 Sep 2024 10:40:56 +0200 Subject: [PATCH 4/5] refactor(regex-tester): better description --- src/tools/regex-tester/index.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/tools/regex-tester/index.ts b/src/tools/regex-tester/index.ts index 9cc542f0..62a5e234 100644 --- a/src/tools/regex-tester/index.ts +++ b/src/tools/regex-tester/index.ts @@ -4,7 +4,7 @@ import { defineTool } from '../tool'; export const tool = defineTool({ name: 'Regex Tester', path: '/regex-tester', - description: 'Regex Tester', + description: 'Test your regular expressions with sample text.', keywords: ['regex', 'tester', 'sample', 'expression'], component: () => import('./regex-tester.vue'), icon: Language, From 1c35ac37043f05bd9d0c7a026dd67d82aa026796 Mon Sep 17 00:00:00 2001 From: Corentin THOMASSET Date: Fri, 27 Sep 2024 14:49:11 +0200 Subject: [PATCH 5/5] docs(author): updated author links (#1316) --- README.md | 2 +- locales/de.yml | 2 +- locales/en.yml | 2 +- locales/es.yml | 6 +++--- locales/fr.yml | 2 +- locales/pt.yml | 2 +- locales/uk.yml | 2 +- locales/vi.yml | 2 +- locales/zh.yml | 2 +- package.json | 16 ++++++++-------- src/layouts/base.layout.vue | 2 +- 11 files changed, 20 insertions(+), 20 deletions(-) diff --git a/README.md b/README.md index b9726864..93c7aa73 100644 --- a/README.md +++ b/README.md @@ -117,7 +117,7 @@ Big thanks to all the people who have already contributed! ## Credits -Coded with ❤️ by [Corentin Thomasset](//corentin-thomasset.fr). +Coded with ❤️ by [Corentin Thomasset](https://corentin.tech?utm_source=it-tools&utm_medium=readme). This project is continuously deployed using [vercel.com](https://vercel.com). diff --git a/locales/de.yml b/locales/de.yml index 5a47c85d..e59ca114 100644 --- a/locales/de.yml +++ b/locales/de.yml @@ -38,7 +38,7 @@ about: # Über IT-Tools Diese wunderbare Website, erstellt mit ❤ von [Corentin - Thomasset](https://github.com/CorentinTh), sammelt nützliche Tools für + Thomasset](https://corentin.tech?utm_source=it-tools&utm_medium=about), sammelt nützliche Tools für Entwickler und Menschen, die in der IT arbeiten. Wenn du sie nützlich findest, teile sie gerne mit Personen, von denen du denkst, dass sie sie ebenfalls nützlich finden könnten, und vergiss nicht, sie in deiner diff --git a/locales/en.yml b/locales/en.yml index d09d435a..d1cd21c4 100644 --- a/locales/en.yml +++ b/locales/en.yml @@ -30,7 +30,7 @@ about: content: > # About IT-Tools - This wonderful website, made with ❤ by [Corentin Thomasset](https://github.com/CorentinTh) , aggregates useful tools for developer and people working in IT. If you find it useful, please feel free to share it to people you think may find it useful too and don't forget to bookmark it in your shortcut bar! + This wonderful website, made with ❤ by [Corentin Thomasset](https://corentin.tech?utm_source=it-tools&utm_medium=about) , aggregates useful tools for developer and people working in IT. If you find it useful, please feel free to share it to people you think may find it useful too and don't forget to bookmark it in your shortcut bar! IT Tools is open-source (under the MIT license) and free, and will always be, but it costs me money to host and renew the domain name. If you want to support my work, and encourage me to add more tools, please consider supporting by [sponsoring me](https://www.buymeacoffee.com/cthmsst). diff --git a/locales/es.yml b/locales/es.yml index b87502fc..2d8b2515 100644 --- a/locales/es.yml +++ b/locales/es.yml @@ -30,7 +30,7 @@ about: content: > # Sobre IT-Tools - Este maravilloso sitio web, hecho con ❤ por [Corentin Thomasset](https://github.com/CorentinTh) , agrega herramientas útiles para desarrolladores y personas que trabajan en IT. Si lo encuentra útil, no dude en compartirlo con las personas que crea que también pueden encontrarlo útil y ¡no olvide marcarlo como favorito en su barra de accesos directos! + Este maravilloso sitio web, hecho con ❤ por [Corentin Thomasset](https://corentin.tech?utm_source=it-tools&utm_medium=about) , agrega herramientas útiles para desarrolladores y personas que trabajan en IT. Si lo encuentra útil, no dude en compartirlo con las personas que crea que también pueden encontrarlo útil y ¡no olvide marcarlo como favorito en su barra de accesos directos! IT Tools es de código abierto (under the MIT license) y gratis, y siempre lo será, pero me cuesta dinero alojar y renovar el nombre de dominio. Si desea apoyar mi trabajo y animarme a agregar más herramientas, considere apoyarme a través de[sponsoring me](https://www.buymeacoffee.com/cthmsst). @@ -39,7 +39,7 @@ about: IT Tools está creado en Vue.js (Vue 3) con la biblioteca de componentes Naive UI y Vercel lo aloja y lo implementa continuamente. En algunas herramientas se utilizan bibliotecas de código abierto de terceros; puede encontrar la lista completa en [package.json](https://github.com/CorentinTh/it-tools/blob/main/package.json) archivo del repositorio. ## ¿Encontraste un error? ¿Falta una herramienta? - + Si necesita una herramienta que actualmente no está presente aquí y cree que puede ser útil, puede enviar una solicitud de función en el [issues section](https://github.com/CorentinTh/it-tools/issues/new/choose) en el repositorio de GitHub. Y si encontró un error o algo no funciona como se esperaba, presente un reporte de error en el [issues section](https://github.com/CorentinTh/it-tools/issues/new/choose) en el repositorio de GitHub. @@ -68,4 +68,4 @@ tools: math: Math measurement: Measurement text: Text - data: Data \ No newline at end of file + data: Data diff --git a/locales/fr.yml b/locales/fr.yml index 35c7df2e..cd5cc0e8 100644 --- a/locales/fr.yml +++ b/locales/fr.yml @@ -29,7 +29,7 @@ about: content: > # À propos de IT-Tools - Ce merveilleux site, fait avec ❤ par [Corentin Thomasset](https://github.com/CorentinTh), regroupe des outils utiles pour les développeurs et les personnes travaillant dans l'informatique. Si vous le trouvez utile, n'hésitez pas à le partager et n'oubliez pas de le mettre dans vos favoris ! + Ce merveilleux site, fait avec ❤ par [Corentin Thomasset](https://corentin.tech?utm_source=it-tools&utm_medium=about), regroupe des outils utiles pour les développeurs et les personnes travaillant dans l'informatique. Si vous le trouvez utile, n'hésitez pas à le partager et n'oubliez pas de le mettre dans vos favoris ! IT Tools est open-source (sous licence MIT) et gratuit, et le restera toujours, mais cela me coûte de l'argent pour l'héberger et renouveler le nom de domaine. Si vous voulez soutenir mon travail, et m'encourager à ajouter plus d'outils, n'hésitez pas à me [soutenir](https://www.buymeacoffee.com/cthmsst). diff --git a/locales/pt.yml b/locales/pt.yml index 96fdaed4..822bea8a 100644 --- a/locales/pt.yml +++ b/locales/pt.yml @@ -30,7 +30,7 @@ about: content: > # Sobre o IT-Tools - Este site maravilhoso, feito com ❤ por [Corentin Thomasset](https://github.com/CorentinTh), junta ferramentas úteis para desenvolvedores e outras pessoas que trabalham com TI. Se você achar o site útil, fique à vontade para compartilhar com quem também possa gostar e não esqueça de salvar o bookmark na sua barra de atalhos! + Este site maravilhoso, feito com ❤ por [Corentin Thomasset](https://corentin.tech?utm_source=it-tools&utm_medium=about), junta ferramentas úteis para desenvolvedores e outras pessoas que trabalham com TI. Se você achar o site útil, fique à vontade para compartilhar com quem também possa gostar e não esqueça de salvar o bookmark na sua barra de atalhos! O IT Tools é código aberto (sob a licença MIT), é gratuito, e sempre será, mas custa dinheiro para hospedar e renovar o domínio. Se quiser apoiar meu trabalho e me encorajar a adicionar mais ferramentas, por favor considere [ser patrocinador](https://www.buymeacoffee.com/cthmsst). diff --git a/locales/uk.yml b/locales/uk.yml index 2d28f157..ad455a7d 100644 --- a/locales/uk.yml +++ b/locales/uk.yml @@ -30,7 +30,7 @@ about: content: > # Про IT-Tools - Цей чудовий вебсайт, створений з ❤ [Corentin Thomasset](https://github.com/CorentinTh), агрегує корисні інструменти для розробників і людей, які працюють в сфері IT. Якщо вам це корисно, будь ласка, поділіться цим з людьми, які, на вашу думку, також можуть знайти його корисним, і не забудьте додати його до закладок у вашій панелі швидкого доступу! + Цей чудовий вебсайт, створений з ❤ [Corentin Thomasset](https://corentin.tech?utm_source=it-tools&utm_medium=about), агрегує корисні інструменти для розробників і людей, які працюють в сфері IT. Якщо вам це корисно, будь ласка, поділіться цим з людьми, які, на вашу думку, також можуть знайти його корисним, і не забудьте додати його до закладок у вашій панелі швидкого доступу! IT Tools є відкритим програмним забезпеченням (під ліцензією MIT) і безкоштовним, і завжди буде таким, але мені коштує гроші для хостингу і продовження доменного імені. Якщо ви хочете підтримати мою роботу і підтримати мене у додаванні нових інструментів, розгляньте можливість підтримки, [спонсоруючи мене](https://www.buymeacoffee.com/cthmsst). diff --git a/locales/vi.yml b/locales/vi.yml index 9eb16bf0..de574a6c 100644 --- a/locales/vi.yml +++ b/locales/vi.yml @@ -30,7 +30,7 @@ about: content: > # Về IT-Tools - Website tuyệt vời này, được tạo ra bằng ❤ bởi [Corentin Thomasset](https://github.com/CorentinTh), tổng hợp các công cụ hữu ích cho nhà phát triển và những người làm việc trong lĩnh vực IT. Nếu bạn thấy nó hữu ích, xin đừng ngần ngại chia sẻ cho những người mà bạn nghĩ sẽ thấy nó hữu ích và đừng quên đánh dấu nó trong thanh lối tắt của bạn! + Website tuyệt vời này, được tạo ra bằng ❤ bởi [Corentin Thomasset](https://corentin.tech?utm_source=it-tools&utm_medium=about), tổng hợp các công cụ hữu ích cho nhà phát triển và những người làm việc trong lĩnh vực IT. Nếu bạn thấy nó hữu ích, xin đừng ngần ngại chia sẻ cho những người mà bạn nghĩ sẽ thấy nó hữu ích và đừng quên đánh dấu nó trong thanh lối tắt của bạn! IT Tools là mã nguồn mở (dưới giấy phép MIT) và miễn phí, và sẽ luôn như vậy, nhưng tôi phải trả tiền để lưu trữ và gia hạn tên miền. Nếu bạn muốn hỗ trợ công việc của tôi, và khích lệ tôi thêm nhiều công cụ hơn, hãy xem xét hỗ trợ bằng cách [tài trợ cho tôi](https://www.buymeacoffee.com/cthmsst). diff --git a/locales/zh.yml b/locales/zh.yml index 160fe1fa..9b065682 100644 --- a/locales/zh.yml +++ b/locales/zh.yml @@ -30,7 +30,7 @@ about: content: > # 关于 IT-Tools - IT-Tools 由 [Corentin Thomasset](https://github.com/CorentinTh) 用 ❤ 开发,汇集了对开发人员和 IT 从业者有用的工具。如果对您有帮助,请将其分享给您的朋友,并且添加到收藏夹中! + IT-Tools 由 [Corentin Thomasset](https://corentin.tech?utm_source=it-tools&utm_medium=about) 用 ❤ 开发,汇集了对开发人员和 IT 从业者有用的工具。如果对您有帮助,请将其分享给您的朋友,并且添加到收藏夹中! IT-Tools 永久免费且开源(MIT 许可证),但需要资金用于托管和续订域名。如果您想支持我的工作,并鼓励我添加更多工具,请考虑通过 [赞助我](https://www.buymeacoffee.com/cthmsst) 进行支持。 diff --git a/package.json b/package.json index f5dedc0c..8a1c069f 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,14 @@ { "name": "it-tools", "version": "2024.5.13-a0bc346", + "packageManager": "pnpm@8.15.3", "description": "Collection of handy online tools for developers, with great UX. ", + "author": "Corentin Th (https://corentin.tech)", + "license": "GNU GPLv3", + "repository": { + "type": "git", + "url": "https://github.com/CorentinTh/it-tools" + }, "keywords": [ "productivity", "converter", @@ -13,12 +20,6 @@ "developer-tools", "developer-productivity" ], - "author": "Corentin Th (https://github.com/CorentinTh)", - "license": "GNU GPLv3", - "repository": { - "type": "git", - "url": "https://github.com/CorentinTh/it-tools" - }, "scripts": { "dev": "vite", "build": "vue-tsc --noEmit && NODE_OPTIONS=--max_old_space_size=4096 vite build", @@ -145,6 +146,5 @@ "vitest": "^0.34.0", "workbox-window": "^7.0.0", "zx": "^7.2.1" - }, - "packageManager": "pnpm@8.15.3" + } } diff --git a/src/layouts/base.layout.vue b/src/layouts/base.layout.vue index 62ac5113..ef534209 100644 --- a/src/layouts/base.layout.vue +++ b/src/layouts/base.layout.vue @@ -81,7 +81,7 @@ const tools = computed(() => [
© {{ new Date().getFullYear() }} - + Corentin Thomasset