From c673616c059607928fbad9f48c383bc7a0e47106 Mon Sep 17 00:00:00 2001 From: Mikhail Chechnev Date: Thu, 14 Dec 2023 12:12:52 +0300 Subject: [PATCH] =?UTF-8?q?=D0=94=D0=BE=D0=B1=D0=B0=D0=B2=D0=BB=D0=B5?= =?UTF-8?q?=D0=BD=D1=8B=20=D0=B4=D0=BE=D0=BF=D0=BE=D0=BB=D0=BD=D0=B8=D1=82?= =?UTF-8?q?=D0=B5=D0=BB=D1=8C=D0=BD=D1=8B=D0=B5=20=D0=BA=D0=BE=D0=BC=D0=BC?= =?UTF-8?q?=D0=B5=D0=BD=D1=82=D0=B0=D1=80=D0=B8=D0=B8,=20=D0=BF=D1=80?= =?UTF-8?q?=D0=BE=D0=B2=D0=B5=D0=B4=D0=B5=D0=BD=D0=B0=20=D0=BF=D0=B5=D1=80?= =?UTF-8?q?=D0=B5=D1=81=D0=B1=D0=BE=D1=80=D0=BA=D0=B0=20=D0=BF=D1=80=D0=BE?= =?UTF-8?q?=D0=B5=D0=BA=D1=82=D0=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Controllers/P8PanelsController.cs | 6 +++++ Module.cs | 21 ++++++++++++++++++ bin/P8-Panels-ParusOnlineExt.dll | Bin 20480 -> 20480 bytes bin/P8-Panels-ParusOnlineExt.pdb | Bin 40448 -> 40448 bytes ...usOnlineExt.csproj.AssemblyReference.cache | Bin 65934 -> 58199 bytes obj/Debug/P8-Panels-ParusOnlineExt.dll | Bin 20480 -> 20480 bytes obj/Debug/P8-Panels-ParusOnlineExt.pdb | Bin 40448 -> 40448 bytes 7 files changed, 27 insertions(+) diff --git a/Controllers/P8PanelsController.cs b/Controllers/P8PanelsController.cs index 7631069..944706a 100644 --- a/Controllers/P8PanelsController.cs +++ b/Controllers/P8PanelsController.cs @@ -8,19 +8,23 @@ using System.Text; using System.Web.Mvc; using System.Xml; +//MVC-контроллеры для обработки запросов от WEB-приложения "Парус 8 - Панели мониторинга" (и прочих клиентов) namespace P8PanelsParusOnlineExt.Controllers { + //Корневой контроллер public class P8PanelsController : Controller { private readonly IContextualParusDatabaseFactoryProvider _databaseProvider; private readonly static string _STATUS_ERR = "ERR"; private readonly static string _STATUS_OK = "OK"; + //Конструктор public P8PanelsController(IContextualParusDatabaseFactoryProvider databaseProvider) { _databaseProvider = databaseProvider; } + //Преобразование данных запроса в строку private string GetRequestContentAsString() { using (var receiveStream = Request.InputStream) @@ -103,6 +107,7 @@ namespace P8PanelsParusOnlineExt.Controllers return MakeRespond(status: _STATUS_OK, payload: payload); } + //Обработка POST-запросов на P8Panels/Process [HttpPost] public ActionResult Process() { @@ -129,6 +134,7 @@ namespace P8PanelsParusOnlineExt.Controllers } } + //Обработка POST-запросов на P8Panels/GetConfig [HttpPost] public ActionResult GetConfig() { diff --git a/Module.cs b/Module.cs index 081cd78..8c8671b 100644 --- a/Module.cs +++ b/Module.cs @@ -10,9 +10,11 @@ using System.Xml; using System.IO; using CommonActivities.Activities; +//"Панели" - расширение для "ПАРУС 8 Онлайн" (библиотека для сервера приложений) namespace P8PanelsParusOnlineExt { + //Настройки расширения public class P8PanelConfig { private List _menuApps = new List(); @@ -23,13 +25,17 @@ namespace P8PanelsParusOnlineExt private string _panelsUrlBase; + //Конструктор public P8PanelConfig(string confiFileName) { + //Читаем указанный файл конфигурации как XML XmlDocument doc = new XmlDocument(); doc.Load(confiFileName); XmlNode section = doc.DocumentElement.SelectSingleNode("/CITK.P8Panels"); + //Обходим десериализованный XML foreach (XmlNode sectionNode in section.ChildNodes) { + //Настройки пунктов меню приложений if (sectionNode.Name == "MenuItems") { foreach (XmlNode menuAppNode in sectionNode.ChildNodes) @@ -50,6 +56,7 @@ namespace P8PanelsParusOnlineExt } } } + //Настройки панелей if (sectionNode.Name == "Panels") { _panelsUrlBase = sectionNode.Attributes["urlBase"].Value; @@ -69,25 +76,32 @@ namespace P8PanelsParusOnlineExt } } + //Поиск панели в настройке по наименованию public P8Panel FindPanelByName(string name) { return _panels.Find(panel => panel.name == name); } + //Список приложений для подключения панелей public List menuApps { get => _menuApps; } + //Список подключаемых к приложениям пунктов меню панелей public List menuItems { get => _menuItems; } + //Настройки панелей public List panels { get => _panels; } + //Базовый URL к WEB-приложению "Парус 8 - Панели мониторинга" public string panelsUrlBase { get => _panelsUrlBase; } } + //Приложение панели public class P8PanelMenuApp { public string name { get; set; } } + //Элемент меню панели public class P8PanelMenuItem { public string app { get; set; } @@ -99,6 +113,7 @@ namespace P8PanelsParusOnlineExt public string panelName { get; set; } } + //Параметры панели public class P8Panel { public string name { get; set; } @@ -109,6 +124,7 @@ namespace P8PanelsParusOnlineExt public bool showInPanelsList { get; set; } } + //Точка входа в модуль расширения public class Module : ExtensionModuleBase { @@ -124,9 +140,12 @@ namespace P8PanelsParusOnlineExt public override bool HasViews => false; + //Конструктор public Module() { + //Читаем и десериализуем настройки P8PanelConfig pconf = new P8PanelConfig(_configFile); + //Вешаем хуки на создание элементов меню для всех упомянутых в настройках приложений pconf.menuApps.ForEach(menuApp => { _hooks.Add(MainMenuProcessorHook.Make(menuApp.name, mainMenu => { pconf.menuItems.ForEach(menuItem => { @@ -139,6 +158,7 @@ namespace P8PanelsParusOnlineExt return mainMenu; })); }); + //Вешаем хуки на нажатие всех сформированных элементов меню Dictionary> menuItemsActions = new Dictionary>(); pconf.menuItems.ForEach(menuItem => { if (!menuItem.separator) @@ -162,6 +182,7 @@ namespace P8PanelsParusOnlineExt _hooks.Add(MainMenuItemBuilderHook.Make(menuItemsActions)); } + //Путь к файлу конфигурации расширения public static string configFile { get => _configFile; } } } diff --git a/bin/P8-Panels-ParusOnlineExt.dll b/bin/P8-Panels-ParusOnlineExt.dll index 001dae8b86e8b392615fe55317b0f8794ca08e77..44eaeafd5e51826047ab7ead6465e33feda1fb25 100644 GIT binary patch delta 265 zcmZozz}T>WaY6@k#<8l6-TdkfVoI~+8Nfh;4@7Y=7&3_|)j`FMaw5d0L&eIF)Ro9j zzNN0hBBnH1eln8=h|w%RSxdtwL`-P`RJk7;!ib4bu_a6hu~w*94U(}dpkgKh2z4Fu zn@?$M6BC$I~VH@YUcglzEuk&jUY(C)TzzG24G&9iv delta 265 zcmZozz}T>WaY6@ktdq;eZhm!#*NXl63}B$a2ckF_44Gal7D2_1aw5dKp<-o7>N4~v z-%?j$d9B#4Kbc7b#3+2URJk7;!iZL=*b*j$SS3`f2FchtP%#q$gt{92 z&8IZBi3xQ7}lf!u^R(JP_RpI a;ndalr6Ua8*FSc2)@Wb6b@Kr?2TlOGc|G(1 diff --git a/bin/P8-Panels-ParusOnlineExt.pdb b/bin/P8-Panels-ParusOnlineExt.pdb index 5c569bc3a3f9ed944984b85a73821a9e3364d95b..5601bbc34937923682a9c83218ad0ceea07285ca 100644 GIT binary patch delta 2332 zcmXZd3v5qU9Ki8&ZvXASWkYFcP1U3L|9h!Nr=}iNT2)p2i=u10300<@_nYVskE zQ52iU5RaM1WkxJpwpg;P5+kxLVUuhoS<~>>YCRc6q;)=Sh8^G#`#{n-K2&&|}xG6S+4wcP`%Da$v7BnY&~|%$P1Ifz&Il zfBSs?&;LD+|E9!uD{fWJ_Ws3pYmR?;dC|K~UoF<>osElpDWWWAaHujxwMr`R8LKzl zRI`!-zL=&hA!lpS7e4h@iBC-q23)ORKvt+@L6dkhXsZ3CKIKaexb{m9$hXz>WRqA+ zoUhKf@iuXRiZXQ^NL;99=;&-Vm$!;NC82G4`Rp5>s#^_QeM5 zhkI}Up21YShy(E&rs0n`2!9cxO1#FweG2@T^#t_;Ji{U6&v7Wm@`S^%GY-c9W?+9D zfdg#(A!7MDrY@Fq_&%@E=74mf<#&A$cAs3h6SX_&F_>Si`)HhaMegMbO zeh~BVB#y@mH~~M!JQW(+p=u)8EwT{a#sd5aC*eJuj1O@NKEgu$2lcQ0i_^#-<8%x+ zgebz+$b(yLuo&Z!F|s=18<>c1Vw7m%+#4D%qi2zD4^f8EI9o*zPmO-dtIqSP6>7@x z)T)JEl|i<+k640HxC~=)Id;Mon1CyhNg`HZZ(NO;xCZHzSc^QIcn9ZW6)r;EL29nl zgvDRA5Xzqs-PPv!D7AHX9Bc3d)?zc(tHBxTGB=UwUcHCM9F+po^|@< zmrK9yL5?`|qIG;$n7@ERvKZ=}YFZkUOmkTdti1+{Hjp1h=PPcx&|QPbmH>qJlgK1}VO>QncN+3qo} zBp_F)%o3AWNnEL#+<1k!N5zJ{hh8^?ERt( z>hYt^(nH=2*%3t&vLm`qLH&A)yj+iK58BJI7wXrb+bs-`+j^CAbG@Ejw|FP80^OW< z>3(o{m+lAVJEVKob}6d4wsfIKLs>??xo*>)N9}-}LNlu%is7p$`T9 zAVa){iJl=$r(S?8Uu%|EpNGT9D{wg0V+OAGY()J-yS@AUD%87M~#nz z3>7Nx5X{rfWaIES>KA(f^=-cOY{q4#>~ogPO$w7`s;R>CmvMG?(Mz4mj&<%-Bn9K9pfl|Npe$Mlb*X delta 2329 zcmXZdd2AF_9KiASW|wZuz0v~ZYLP;BJDe?NA(TQ-5NNqtj+RrPQWTVe$g#8Z;uN}1 zkSkz041{&!#M&wbWDx_Q*hd-B$U7OG{^1nUIF_Ts2#__7-zR%lI}zSUw>{EJkA-w!*fmbNZlQJdq^ofGw~iw!}_IPIN|c zqKjISo-Dhn!|4-4-O1^DdSDVh_~)e+aN~4LCST&_XS?xx7$mj9-HZqQQ z2V-z4Qf}g1q@V;vU{O$F8FKid0y%uK95ZnRGHLNX>H=Dcj3qum#&8z6)-{By$gdMZ z`7-=nS95)o9R1dDq~AJ$7Jt`pof?u+nOQ@mSG6AXOgCUOZbTjsu?ZqK4hVT(*snytrkLWMa zOVfwKqbzEX0&@=MJnF-_fE(?yd{e4VioBjFV!7IyA7`H)U0}$Fl4DJ|&+avLf%NGW zaw5(T;6YVaJVqW?jm2h+ekSyJSJ?ikKYQdtb#I1A8&_h=GL`AHi)r6d zyPWpx5>pifz3OpEz%j8jAj?&LsYzQ=YDQAL>QHF_?CYgz-k{Wvm+T~$L|K=lb;$^~ zi3-n>;aO4Z2Fi5+-S{XDq5l}BQ|^@>Ax05bdAS&@ z3Kz5sX6bGs{en4;dSe?<5A&VtHO#T=7POIm_S`8zUGw^!#;CIk2g$MO?}eruuj0#0 zS*WsUC)!KPl0C9m?J75Y`Zdr^B&$=|arW)wG}-L!C-$^%pP47?v07!K7!u!t-h7#Njmp;Y9Ct?v?RAHUhkfR5IHKH_<7 z-OMe6pg%Yoy2QyYy{ooOj9rye6s3S+u>u~6o$pccProkIKjU z>Ll)be)D2+ejNdM@K1~qA8zAfq~KRnnnSAG(jm7nv8}GQ=q!A07s=W+W;R}SFzl!_ zkdlqx$>Y+6p6Lqw9TmqR7b>5xPER$Lmzzx?>g7gDWvSVe6dx87s|$-KD8@u`S+a-Z zfnvI1s1$*J-G#v}8i|VmZw;imdQ-VjgCH1Heb>5^89YP<{HM!{p#2j;RRhhB!8BLw1 zg%3#rBVePQW5jG#oUHGMLR@~bucv?+hw6|jg?bSv#z!ch^nI-|54tBZVdMij zsI7|~S$pS}9?qALavrKTaH9?T{UhnSAtk7+pZp2JsP}}S8dwnEPNmyTcI-TUat!t; z`$pwKm-8ofopZ!d-%9dIm^)JdUl{4Wx$!c(){2Yl)Oukvnno^zz!w(I%|dt@%PI@r zFj$Pm&j2+Zg9@HrdH>5_IkX0?!ZBLNNN@}(4JOz&bDub&F*2*KujkoK>kXEw$|=l7 zV#cMHrAc7Yu=QDaMPal?Gz6`u&6E}%#}L%90&$GxQcTAkymfRjsG{~yB8D^(0XaFg z>~N@#n&b9M3!keC&W7mml#F{x#zQI%tPEEo=2V39%+W<~^QeWP@FE-s)#jkR|1XBy zOjA^bE1^hNfZZW!;oRNU9mh+gT!iEg?2CF3MOd+$SQDa&EbSx9?3z?4lKSBT|It|N zu6*@!n7+?J%*lmO6>GvQzZzGGpQjTNWcT(aVYazX4`4&)r^~S6ajFGBJG031l?(2W z(whx;mbk+4oSE46zCO`*_~wc^P=8VhoCvp$%OGNngw4n+6WKN-7YE@DPtNJEF?3lB z?ZSsfcb5w43ui&c%ii23_Tb8I#WXguHH8Z${OgcmJI%i?ef>u<&S8I9l;2tZGQQ!m zG-KsDtGQxIv(atJ(esK$11aU3FmAlkw$x-JV&ynq3ujE^%CdE5QuNx*sWQJaTQFXQ z(mNB$_$nl+ zW{Yu33F{d)w|XaWZ)Mo~HTUd*b!XtCdL`?#IY;nks+USJI)A;h#1^-CRwO*qE7_*T zW&vAO(expZ!F)m!O5KRfWy~sw9x-l)=eS1tyW6rQGzt-_n q4%F`jY{_`0y*PM)-=7}r$o*wf9-80>H-wX}k6z+W9xkDRsDA-8#p-VW delta 4121 zcmb7Hdr*|u73bRr->xigc6l!0AxIY4WqH51JOz0Q1O=4vxh%M_?85E>5<$Ww8Ix*6 zIJL%+A#3`YOw|~_GPX6gA=X+u#*sE z_nhDTopXNY^5HL~$6t`07^|Ut&_7C!{!`f<&OvLBozdHELwmZ{Afvpghv|vv?n$qXt+=i`NS zmYU>s(F5f-;fyqaY<`PGhr7~hss+wULm^idtl%N!!SL?HxfmrJlJybempI4yS`Aqu z9DB=!mrY(B}XT?qj&r&sV2~< z;)P?`!ZCEcU2yL;1w6d*4LD;6C8yk*P?|?}2Dls4pHslpQZ+;y#O!!6u&fyaPoe^b z`bVK_DiMwZhS2A}sKCJH{5kee1bijWDIKf^hHb4WcMJ|X?7J=dx5u?voGz=wUYw`T z&N1rq_;h6D@%M!8pk4w6CHib%DtsAqkt`8Oh)gyvBws4ee5D%E*QE|8J7ZidP#06x zu&j<0IpB*-30lns-Uqv^*-p{FDsLeyJ~D2D#+eYfFsXy9Y6a_vP*H+Qulp`VPLp2| zIm?<6?_4(fCBVbILBaYSn~frkG>~K=u4gj21fd$hMBMSy!RhE|l%&OIF-f`E_|BJN zlw450vb_p$L$p86pjMs$vP!tu=GVXF)2K5!=c4p9O zhDQPUP(g=4MtoM>tDo(}5RsK{y`#rsb5RN;E=Gxu4^{-!OkA-S##eFMPr{m=DU<}R z;SKoeLwCXXo%P^ZP{3qoC91~`Ax9YgM`i_>w$zA~Uz8CdBvz1%+@w7E&HQ%4=JQ#c zTp;Layuy?T%&>QxTO6jlpUGD94#*MwzF20^iJ8&{Gq;7S>T-yGtSG>tjsL~0<# zD3{K6qVheP!U-BuFdXxPlme;}0-n~;d`G}TbsFq`db4o&hPPx~ryAr?sPFt7EY%^NRy zm{0JxG1aM|jW%XzUD=&B0CF^!xu5v?s!(G}wGD0X`9dT7TE?Y~Oav}%|H`t1gxLwL zwaxJ2mTFS#W7#7TN+Gre`Z)}@MkwDJtxm@7V$5#1_g*pl!CX(yqW+1+Mv=TxrQL0D z4mqtZON+%hYBgJ2Vk`YKyGX9O6I*_hEzIesfqH5uiM-d+A#@@^kzMjEgp{Zyl!hSr z%g^h`HU^4jF5`Jy4=%WO*|m(|97fMQQ%l*rV^Tz7<#eIR3)KVD2MdR z!DL!_a{SmYO*V;W@Sr(GG`K6(0XF!kEL-l!dq6bALU(=`)b5BD4B7qF*Q9(E>*`8n z{O3^9D{}sG^_kyGNp0g>;LgIGf-{Wq-EYs9+yC5z^eDDNqr}tWumOz{pt?;k(J@I{ znLHCl`8lvh&=K6uDkG<1L^Rfo?c00H>FY=Oi1e3aZY7>)iRbtg6PnXObNl?@^?f&p zH}Ms>DpK*5Z_K6cwl!)fh##xx;B$r$p!#f%X1}M|JG`y&c@> z=N~to0}~RSm-vAf*ZiA;*HO=g+2`f!NW+BTZpWnk%vCD_Ee*?nxD^ddT*zXNx!a}U zh9@kMY@nA9+jx+X(2XCq5jr}yaipOMhEYCv?lB>OOfX@ToP?iDEYe@NTgi##L(zo5 zX+j{AV}g5WzU;@7iwJDuk4E%O_D$sW{Fm+wWX1#P$BLDv6Aj}#F%A@JA9c4}-Et?GpE-ec} zWUmm6e;)aje;&7|R)gtP?oElX2=ll9_&ee~0~Qk4#u&tE*vD;gZXSBU?L zU@tCq3P6J{FAJZa{@5rJ3IPvf{v}P?HR);%Z63`gt<;D9ij7-A8XV!zUb(8HMIMCS z{`)T~_@*kl9xmfQ_uQNkg!PZ_pW%fSihoE@p}J diff --git a/obj/Debug/P8-Panels-ParusOnlineExt.dll b/obj/Debug/P8-Panels-ParusOnlineExt.dll index 001dae8b86e8b392615fe55317b0f8794ca08e77..44eaeafd5e51826047ab7ead6465e33feda1fb25 100644 GIT binary patch delta 265 zcmZozz}T>WaY6@k#<8l6-TdkfVoI~+8Nfh;4@7Y=7&3_|)j`FMaw5d0L&eIF)Ro9j zzNN0hBBnH1eln8=h|w%RSxdtwL`-P`RJk7;!ib4bu_a6hu~w*94U(}dpkgKh2z4Fu zn@?$M6BC$I~VH@YUcglzEuk&jUY(C)TzzG24G&9iv delta 265 zcmZozz}T>WaY6@ktdq;eZhm!#*NXl63}B$a2ckF_44Gal7D2_1aw5dKp<-o7>N4~v z-%?j$d9B#4Kbc7b#3+2URJk7;!iZL=*b*j$SS3`f2FchtP%#q$gt{92 z&8IZBi3xQ7}lf!u^R(JP_RpI a;ndalr6Ua8*FSc2)@Wb6b@Kr?2TlOGc|G(1 diff --git a/obj/Debug/P8-Panels-ParusOnlineExt.pdb b/obj/Debug/P8-Panels-ParusOnlineExt.pdb index 5c569bc3a3f9ed944984b85a73821a9e3364d95b..5601bbc34937923682a9c83218ad0ceea07285ca 100644 GIT binary patch delta 2332 zcmXZd3v5qU9Ki8&ZvXASWkYFcP1U3L|9h!Nr=}iNT2)p2i=u10300<@_nYVskE zQ52iU5RaM1WkxJpwpg;P5+kxLVUuhoS<~>>YCRc6q;)=Sh8^G#`#{n-K2&&|}xG6S+4wcP`%Da$v7BnY&~|%$P1Ifz&Il zfBSs?&;LD+|E9!uD{fWJ_Ws3pYmR?;dC|K~UoF<>osElpDWWWAaHujxwMr`R8LKzl zRI`!-zL=&hA!lpS7e4h@iBC-q23)ORKvt+@L6dkhXsZ3CKIKaexb{m9$hXz>WRqA+ zoUhKf@iuXRiZXQ^NL;99=;&-Vm$!;NC82G4`Rp5>s#^_QeM5 zhkI}Up21YShy(E&rs0n`2!9cxO1#FweG2@T^#t_;Ji{U6&v7Wm@`S^%GY-c9W?+9D zfdg#(A!7MDrY@Fq_&%@E=74mf<#&A$cAs3h6SX_&F_>Si`)HhaMegMbO zeh~BVB#y@mH~~M!JQW(+p=u)8EwT{a#sd5aC*eJuj1O@NKEgu$2lcQ0i_^#-<8%x+ zgebz+$b(yLuo&Z!F|s=18<>c1Vw7m%+#4D%qi2zD4^f8EI9o*zPmO-dtIqSP6>7@x z)T)JEl|i<+k640HxC~=)Id;Mon1CyhNg`HZZ(NO;xCZHzSc^QIcn9ZW6)r;EL29nl zgvDRA5Xzqs-PPv!D7AHX9Bc3d)?zc(tHBxTGB=UwUcHCM9F+po^|@< zmrK9yL5?`|qIG;$n7@ERvKZ=}YFZkUOmkTdti1+{Hjp1h=PPcx&|QPbmH>qJlgK1}VO>QncN+3qo} zBp_F)%o3AWNnEL#+<1k!N5zJ{hh8^?ERt( z>hYt^(nH=2*%3t&vLm`qLH&A)yj+iK58BJI7wXrb+bs-`+j^CAbG@Ejw|FP80^OW< z>3(o{m+lAVJEVKob}6d4wsfIKLs>??xo*>)N9}-}LNlu%is7p$`T9 zAVa){iJl=$r(S?8Uu%|EpNGT9D{wg0V+OAGY()J-yS@AUD%87M~#nz z3>7Nx5X{rfWaIES>KA(f^=-cOY{q4#>~ogPO$w7`s;R>CmvMG?(Mz4mj&<%-Bn9K9pfl|Npe$Mlb*X delta 2329 zcmXZdd2AF_9KiASW|wZuz0v~ZYLP;BJDe?NA(TQ-5NNqtj+RrPQWTVe$g#8Z;uN}1 zkSkz041{&!#M&wbWDx_Q*hd-B$U7OG{^1nUIF_Ts2#__7-zR%lI}zSUw>{EJkA-w!*fmbNZlQJdq^ofGw~iw!}_IPIN|c zqKjISo-Dhn!|4-4-O1^DdSDVh_~)e+aN~4LCST&_XS?xx7$mj9-HZqQQ z2V-z4Qf}g1q@V;vU{O$F8FKid0y%uK95ZnRGHLNX>H=Dcj3qum#&8z6)-{By$gdMZ z`7-=nS95)o9R1dDq~AJ$7Jt`pof?u+nOQ@mSG6AXOgCUOZbTjsu?ZqK4hVT(*snytrkLWMa zOVfwKqbzEX0&@=MJnF-_fE(?yd{e4VioBjFV!7IyA7`H)U0}$Fl4DJ|&+avLf%NGW zaw5(T;6YVaJVqW?jm2h+ekSyJSJ?ikKYQdtb#I1A8&_h=GL`AHi)r6d zyPWpx5>pifz3OpEz%j8jAj?&LsYzQ=YDQAL>QHF_?CYgz-k{Wvm+T~$L|K=lb;$^~ zi3-n>;aO4Z2Fi5+-S{XDq5l}BQ|^@>Ax05bdAS&@ z3Kz5sX6bGs{en4;dSe?<5A&VtHO#T=7POIm_S`8zUGw^!#;CIk2g$MO?}eruuj0#0 zS*WsUC)!KPl0C9m?J75Y`Zdr^B&$=|arW)