diff --git a/docs/en_US/images/delete.png b/docs/en_US/images/delete.png deleted file mode 100644 index e5936e8278aa04251a7b1d6cc1d85b207330aea4..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 5414 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 KOR)@Y5%fRlJ{N-k diff --git a/docs/en_US/images/download.png b/docs/en_US/images/download.png deleted file mode 100644 index b3efacc7460585684d24b3d7541a8a1c02ec6c26..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 5710 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 PJoOZ1)nv+~OauQ1ScK-1 diff --git a/docs/en_US/images/folder.png b/docs/en_US/images/folder.png deleted file mode 100644 index 473632c4631659932ab07c0e0d5f8ce240870b62..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 5803 zcmZ`+WmHsc*B(G=5G16#L536XAqFYwZbb$J6-A`GK^Pk8?oI*e z{`7g??|q-O-tRkW-RInA@9Wyvjvx0qkx)$~B77Qr002OwqO73v`ziZ-3E^V@zVC+2 zkplpP$`11KP!)N3CaAlst%H*d0H7S1`Wy%LteX;Lq@!XVgsY6#7|EiX{!lKOiAk@7 zG)Y!2Qjj@fl2p63G8%VsP>=NK1ZJ0EY5LRBv+(<=sh*|g@@pFSo7-peSMwK5wP($C z0~cD|vzgQYc!7_O191U?Y!RCl|U-%vXa>YiCwEB~I4iOPV)&h`- zkE-v!pgUCG6`?73GDF3Q+a)oWMi5{F4#2bq^heKzogBlS5lOx3Jxe?Q$T|Y+oCO6~ z#*GMHUDwpNw8xb&*n}GhCcMNl!=E*KPhOY3=&|| zHIei(;8GbKjjmKX3SJRuD*h-@O5^vArw{M>_BW;{sT-Xy{0{@cHB4jIhzb$l6G#>( z3e`bN@pS+P2+$71k^>NMEh^(ALnukAy+plQIZxE77BQ&1?#V6Y4juckeYIsfpm~7b zYDR(=iSpjNfZo~2er>7?Bph>U>S3h?zZQR_5KMPo2=!6H&SekcgtFdpgBaJ} zVuic^w40^__Th!{{p?o^c9C8=1M-GD^}QzY%w@KFmV#W6tjm> zNvE;iv;AuIR*7iA)5J>2?PE>~B!wyJdpv4dbD9B*uLl*d!0cJHg@s%r?7ODQJ~GL_ zf532&$6iG;6Q0!?XSGox4`VgAP%7ovW$}VV;^+^Njqz;9Q|9+@(*BBg71cS?uIr`q z({N*Y>(W3fos$n5z=&a227jymj=RUIbSd4eYgzSNKD=bsc+MCDdK>>)=9z0o!5vPh z&uwPWrZnJ|8;L}QH*MuE`qkY@07i>kL02HarV>D0GP^io?W=J4xocb2iL0saX zl|_*n0Ds8NBEPW|{o?&i?0s2aFcVv7oB)YcJ7($AccfzNw0N>|iCk>NDv;p>b%kKA z1nMsE2SS4&U6#xQ!&R|WCU-iC@CxSY#BgQKUo;n?mRv-lvi(p=IMsG+*^sgbMpmG0 z?z2I;3M!Le{T$Iv%?b>uI8)i;yuD3=3LLBqN_0D);G;g;6>~utPg+oSi2;mTKW@zY z1SWi)RcyHjdvr?5xlH)(b$ts3T@dH8zdyb-fmzJ+<(Wh5YqkK2R}tPTW_a*m?$$Sp zYKsri4~6ia;jxFhx9PWGv~iz5@g$iija1+mLT%n(K$BZix`EsT-RRxK4yj6G&od_F zSrTJZ2H0Nd5JoEXu%;%ACwV2sB^4!rlo`7WtqIC#C1T#GrX@sot*z3pvaa&3+O3*K z@pq&xt3|%Y-MlY2|@+F4ED-K2OJL5Ui?osVM*(1u*tj@z3dbZ_r%zkWmiFb*0 ziQ^o03Uw~3lJ%?dO7#jkrPxack<%N|R}Cm+$z{1`AwlWzIyiToR~?-R>L=eE&s<2I zn5W+{mGAcx%VYNw%ALJI$^0|p><_N_j0M0!;P^t}E4e#CEGw9>IH9x^gB8IFdEWOx zdvn(o(Jmn_;Ypi8$3f@MuHtP1-6bt0JqINgl4MrXg0+2g>pJVE>qP7M5ZjQ+kkAlH zq5?*^&7fait0F{EE>9hU>M0y0@!DDq~7?VJ>A(mAjQ?)v6UdWz)`{3vV6woU<$%d+Ivs zX3%Z675#*npiIdsawAux#66lB;i~<;-Myqe%1O~_scNyZjp;|z6H^NwIgTaLi zYSxwE$6kG2#v6z!JkMV*A4=#+n7AuuNo92m?7W)^BMCbvOeFk5?LP8)z0IrJ`-_K< zc#4FGqy5kz`aLjwicpQd%75~Wg_((zv4?SW%{+aPjQ{9C?o$7EvwDfz!?}XlqS}$U z@3VIGVztdQOJF&1%bN%z2EzCu1_H1lxC!Cw(*xd-l5BKp7;Y$Nbn&G{bov5MrFY~H z@J`?Cd30^$73aI6_DvU>Z;Y?YZoJN=7#(DE#NB(lI&bxF!FL+Bdl-d*6@jrBdqHVI z4J~h5lpy1f;GA!eACqyre5abHz2+0<1_wclXLM!*>I0=Dd~DzkA|FI`WkdukgpMH@ zdN5m<3Cz1j>HPS>iZnE$D`JgQtk%|8x;kw}s^`UMpEf6}L*ij#YGQouyIgDS{=A`~ zJjG%?g}7J!h+qr+?zLK1smM!M&XFNms{FXM21U<@SC>KYoX5 zU$DvgIu`Gg44>m&roE7$-SUzOC>fD_`jK=vX~gRTa=qig5h1lTd%S(@A|2iwb|*)| z24mkOza)5$n{9J$SJ;I>ZDrRAl|Lir;(6p5DY2}2__Z*ikjP-a+^VeF=4_2^V|Rdk zXRSh5Pm)`@lmvSDtK`@Z*+f}=;?eR}-%v{0b%U}EbWetVooohH0KfDliX@)+T>*1s%Fn;I{V zw)5`8%PvRqd%B#?%0wAQ>ytNTrGtxWCkqjphbtFLM?0z&YS!#xkIo-YmXMfnnNHSq zA%~`)nyKCYxY29e+tVuzTn9?u^&Xh<1Z){4m45L2vN3$p8_~%#ZIxC!}sKB|o( z{&}3~R7q520eoy`ELlIBmr=XPg2*%0Qp4}5?$Z&&%*x*JfFg1|(_;LhX%lC|#?O~G zpw>FxosjVfSAiL5)zXOKA=)UjO-yujaxBG_!)0LM8m=~+Cfw|MXIMXG{bFhyIKwtG zUES#{W3Z!VRR0~`ISi`M)SjsIxE|=Om-7-Gs~>fp?w>WO!r9f{y*R3_Sa8{mot-KB z;b(ReFmp48LxrPCn-JzeG#8tTKK+#PsVXFoxJu+ol<^$7xj#c}z)%2kLLjzCw-c9H zkxB&dr*z2-J0O(LwOj9pw0cf7s>aK`uY3GiV*UV%SQ5ERc-1#lerxw2>qyG`pyBKS zO@Mkt!|!VhJ_zq*#4(gIqUHB7aje_*sI7Ijo=M~ldLCy+RO@?5b2j~YXJ}%^g>AmZ z)8o4T)F{~KhwH{{fG6jj=Kh?-8Sa_t{?0t`mHB1Px>?-a^xV&>fOCtk@6qwgjC07o zSJ%st*WDX&%lXIoYd`oLpFPO-~w4uhHlIRn@HXRmbh8U_|;=(HU|JXXU|+jPEP(5%BmO4z~j0$t2YWg^AeVtCa^`%@~Ruf%nlimQ25YE%06{8+ZT!lN zhKdf`0RVuB>7WaP!!*=ER<6$c7S^toHv9+&MTQDJy*$G;JeJ$zi?7Kq0#9;|-{`QJDSHXc^)4lm&j zt}aY};#yd`dcvhxSpEq8`}#Xi8-&Aulw3UiRo3qUfqy(eL4EuQYpj6F){G(8%@g!kcP;cn3pnT7tl#Au8o3DH-E8o0ppND| z2Bgjgz7?fEBz}nQkeitDtgpTv_1PryUA47i8M6#C z{eg&WTJ<{1E&WLJ>iIW4NVz zgAjhItQjCI`Vczk3Cgl}b`I%XQ?RsTQRhg0QWnLsRjEyVJMU6$L}*#A$13WHFC-)c zH8kYtsmKUfZHUL~YD>(huBx&`7dpY=@SLXi%+`Ey2%>}}nlA0~?@h+etoigD(PJA? z!c>QV%@YPnPmq*x8=djIIUBjAAREWxPj<=1-tG22?C&pqE>v`NQDH$Wqa`H*y3fr* z6X&0G8oBLGy3ICBL5AMZ66a%0>GM+Z`$H=TVC>`po=O4YLz!v6#kbCUFkf55U}acH zO8W2_v2is?+3duQMWDuK?L3Qv} znjF{oY`CrxR=Ojf|>vkW_6d(C`rrOvKwG?2av_D^20N z&o7CkFAuPyu61OiQOe+PvyC4-3*f98b<7;ydnoP|N6bJ^Ltnj)d<3;Q+W*apFTK)#XGa-^bjlOu&<79Jr0vzYoL5PBLOS3pX2k9w#~WoKSr8O z>pC-5plGXd6$1rDz|7hclJfh`OI8N!okn3|NsN%>ltr^D|7h_y3S5HIvO;_eXS`ehTB zm%hf|z8*~IXXGE*Lvt#>wu1rCj~uh8H9v8ubjUYKm}V904>olk2xDU2?U@) zao=~t#Q%EBMPziG#Pv2EEt?UiK?982$z|1uh>2+*> zxITQ}X|4+E;^N}`I(lxh!VRmeu(o8~+OM&ZN(aTsBvpS>JO{w82?FnFAYLrMt`ttDO>JtdiKHGdwEOt z#nKAI-L23m1`}*aqV4MTCHLvxLVRc_qM`IcgY?S@bQIn9LSCs#)*OF;%CycgT^1)r;+VAFM;0z>F zI4^vPU>t8OE&wF(ba9qviaEGirny9!&tPe3dSI83{3h#SF05_&0@mbD-9d&; zN)k&2pyDFE82VXQUQY1QW(~7GDtVe!c0mPp*VCKvE>qH}?Fd#N5-3?liD0SX0;`s% zBsoE>6+*e5?c7d64qcNKK_^*n(!)EV8Q0&3%8&rRA3%u!M=Tl^-ANsbTA#_V_&RY# zookgw?gd&$iSae{VSm7AP(O{{lcJIBz+YM_@#!w_lgDgnZvAX6Ze1H(R$wDwtsVoA zvw8&R&^*DI+QH5El29(o(NZ?z;Jh zk@+Y7b-oPL6gOb>R$I-u!dZmpFj>v$U2`y-WcwUG_YU96l4j|GM+bFAl*-UZpY;x# zt?0^%wI>lTj!-+l#Lnv)G>na@JSNt<`C*daI{`>_{spF+w|D$3zZ&4~OyUJ#K}4mJ f?f4=*@)h9yUYq?#nJc?LpMEM&H5H2F%!B_2{lMf- diff --git a/docs/en_US/images/gridview.png b/docs/en_US/images/gridview.png deleted file mode 100644 index 41edbac36fa202c6a0eb73d019fb5782dfb0de57..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 5781 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 Wk-H_BD!%)3zE+Y~m#dI55B(oK1D+uO diff --git a/docs/en_US/images/sm_download.png b/docs/en_US/images/sm_download.png new file mode 100644 index 0000000000000000000000000000000000000000..50471b7608e9d6b2e724152da69c497bec70c6e1 GIT binary patch literal 5009 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 P`9Sq98K5h*>?8gMUEqNC literal 0 HcmV?d00001 diff --git a/docs/en_US/images/sm_home.png b/docs/en_US/images/sm_home.png new file mode 100644 index 0000000000000000000000000000000000000000..f6b13b6f8421ed8fb71b155a7736ea90a4a12b98 GIT binary patch literal 5120 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 literal 0 HcmV?d00001 diff --git a/docs/en_US/images/sm_new_folder.png b/docs/en_US/images/sm_new_folder.png new file mode 100644 index 0000000000000000000000000000000000000000..3e04e410ff1ba6322d092b50eefcbbe532e350d4 GIT binary patch literal 5274 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 DJQb~j literal 0 HcmV?d00001 diff --git a/docs/en_US/images/sm_refresh.png b/docs/en_US/images/sm_refresh.png new file mode 100644 index 0000000000000000000000000000000000000000..c7914c0190e994b3c562867af85c8357a082170b GIT binary patch literal 5523 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ℑR7G4+ns6ZdMRU-aX!Qg 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
A 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 z zMn?X;viDJ$n})mEX=*EEr$(|fc;irsd;7UP{WE@L_xnlE^p6qlL}r~*vPFf0`I$V~ z#CcW9>lLiIPU>M>TPTJdOHke*Yiu{mq(L)6Wboyk%=EUHe1v% zR%Sw>mR4YxLvBOA&=cU8ZAd`PZ2IJ<+~Pd#pyZoF8YnfuBYv33Rxyhd3K{lns1DVW zzXe>az1{Y3hP!g%hog2S*@w!SNlRbRh19$iT}(%|HyNYYbHS0&Y&(dT)9+v*Lbj#c4%` zItz2?Fwzd)#x~I1nJi{s-+2DU{ZNj z*?LKG8oLpawUF~)aZHnR6*5W|11IH<%xwY|`qxd-D_Z@2ANOG*Zd9#+?Q zn$4D>#@!Xel)>-WCffIxgLdUDRuy832gX<6P?C-IT{O&lcb^~T&M_6B$>x1Lno+VX zG_m^kQ9xuaPcZ7s^VqBb8nwW4C& zHzvjyrh;agIu1g+8%3;Qv~?OHlsqETTVV-nYL zG;l@DnrDNM8mutIilz5qDoB#h)pnNZ*brm1K~j#V6U%LB)K{KuZPuBk5H)uL?&X}Y zj<~MY@GxbGGpm)AsnnUdzOW@&zYYsJwn)Q9=jVFhNOmVn{$y#n7E6%^%b358V@v;W zRaB6gcSH5mf?W64;yrXqS+pJx_0eIqO=7a$X)7x&V)yNwf=kCH^!QL7+B|CSFVtKc!7;tnjiSSY{u9&{*cZ?AT8(V;|u_tl&@H>Y$ zVzPPME{g*?ci;dxk=RZX{fD0;f!!L7#i5%rz&}rSZq-xS6tc`{3jGeab zdGk!gP_(c1e}z}?YNy{WgMOq%RLRYRppQ@e0yDZMH=UVl)i&pHCgk1b4|2Jt{3Db- zBj}90ybVfYmv=OT9C8p0ber%b(yizkt(<|F%<*BhjuBvsvrum9m6Ct&Nnmf3L z!{Yfr@$Y}kUmG8ouTgE(jajM200HGCyLFN96}@KGLPCu7lsO-E{gF)R?VJz4!+Ria z|J&Mqlk2K*W+}pxBkX_AYyJZPCQ8>AZiln5YlmDW4FuE4uW=RCewJfB1xPP|?z}RA zQCZ(t{tsoKqb4mRK!ooiL5y>;PVgVnGFQjtO}egZzmh2pDZ%PZ{@lf&#FO7&xilQ0 zO&Aj|{I%;%vvHFw-OF^ulj=U!|_l4iL(C;YMqJK;^Ve}hfw z_<|MPud|6d46zxy3j7hClU10C#X5T5J^Yuiv%6dV^>*OJ+eXPadW^g&07s8b_Hb zm)UyvzSB1|V})nFSC-`3>vuueDhJOXNaQ)bzjQgSkQ@i_Hv;3wd(C=8Vom zVoTH?5ZtUmKBX8gwl=2S1r)}UVCa8$iR8dU&=vGI7CYLR0a2GXqXXdAKn#DCGJ_UF0W{~8?^U^PDxIF{Sw*rJXBP7+>-I;Ks>2#b=8>~Hod%C>yI z%yH)Y=NB!*>-8Ukqp?MI`=SZ(U+^XJD6Fpj5yY#Tu}B^0znhTrOZj5@3`;zKusLdW ztqhJb4Y8gBVuRJA@3{Z(4h8i5FY+6p_ZENsFENN;nmBl2kRwb&1u!G^&7}j`luUtHSPR&Toj>s2|gwes~!e>YlP*$nu6Y+Z5rx(dD+s zl`kkwt_*NrqK|{WW_F?Q2Kg@Nb(1Nq(N$kGv7YmE{jvzcfd)R~6h`LNVBt|61Mt-0 zy{|#in;AbB;E{+rE{);%yRgSZbX&iEYY{Xe-nZDJ!kJkEe znL0C|&jvX5a;aY+*e0g?(6>T%NqI1r|6eHa+k|D8Z`1f;59v43{h078d0zJ~10cKu zXd#i>MMIg{~Rgc@W1RID1uI}Kra<*fE5a4G~zm10WFYy2P0O%8E%fCNhA?dlI z$Ny{)n|ja%!v2tWTN4)}iaj(aBcNG^tT0k+h-Je~czZ`QI!G z{%r$%5XgT3;?H-wzm)}$8*BETWrY8P93~e5M?8xBKfnL^EdRIS*1oMVYskd5SMv*& zmYH;p{OgmL-+o`>U5(k#e|_;6&_eIoO-e6pnT=jpfa!2y)-wc_;?etRU5J@GR;EfA zTTx*bJOUh=YO2^Umxoq%mru3WJ1q^Y>6&ogApgG*PzD{TEU77Oi0e*3$dt)@RnwK*?oj&Djbpdb9bS4CHNDrqje+Paww=7N%O zL=A@<+_9P;Ac+%}2|eZ>e|)*Siqm$)!1IYW&gHr9_AW;r)8E(tQZId|_l743vHr*> zzHmK28#ZK(SmCW*F^O*Pw8$7w0p_x{)kVmfKwllPH@J)s<_bB?7x%|thsz2$zR_^w z!dD~UQX|V()Hihcxi7ykeUmL8-Mhn0zJH&9d6nL_O{^g=t`n;TR9qc0UPsDuM6=X% z9dUN`i$Okji%x&~Wk9_kQ|NK9A$XE!h$H&HNPK|*s-^}@CSFE=-*yV$!Xv93M}i@J z+GcD`MiFlX+>C9}P{md>-0Ogo!l5s^%zglSh=ItWL}JkD-#8glH$j?RGKx(b2cHv2 z*yGGH?4s(mBC*sWKL+@tP-r|3>*+-U09Mf|3u0px)df1Avh3b|AAi|t;^5oF17!Nn zd1qn-4X}MfxQxODnmApR#~K09rJxJ7E5BaIS-KK|1(jj|-o96+r(yipw4?AQ;QibC zvT3n&PUb2N0EdL{)v=zMoZNi*+J??R@UqZ=SAC-^nCNK#+Pw2;@9lr>AV$svs&hV; zB^qR=r}h1x{oMa#cSe@4YwvIT5(nk<&fIE!TFbUpdzo9MA$7>K*bR>Tmiam{MeAT2 zgOZ1rG351i7e?P`Ne>sYImmE=TzJyW1}W@bjRQ7&r&2t>l&(_nvaXtB+>P_NohP2} zvXWy`dzpXv7r+p1#O-S%?QDG+r|Ss+2`yzeum89#BVSn=Kn~lFju}4N-oLD3BVPbV z3843Sk3qfd<$jr*Ttr*r;0&xj$y^nWszaI;?hgbI(2MUr%^$x^OyoMis?Dj|{n#F& z$7$LO|K;z6uCJ+FKlIwE$`I^av&nEOY9sYL%KrB`5Ie6J9aqu5qpzJFX z!T%YiM+u`>uq+kOb^-v(Q%_8HVc(ypT^@dTUDriixuycz#|lI5irfRz34}MGtCwZ< z`uanh+jrpCFLzvVIvlV(QL}G3*wG09tDXcguijl&Jm!4W-&$~Xr&Z{Sb`JJmedAPK zhEK3M_xd`Z?YK2~tj<_xTEDSW||(x}+CwOYg%V6P7F$KeK(t z=_BF8W~2=jV2Uu=tQS~A`h0=?y8(SCSDUe<0WdQ90s~(9+C-|6gg0U5hRw96d^d z``9=~bCCuxs=<3;J&tWxecdPi4uIW-bk72z_--`~udwXGk!E+~in5*M+q z=v?q>^tuj*8~#vClrA>3h1Z$i%(gp&G-Ty@o^P1DvSTBSA#jbXbGsJA^N@0~U8esl zRyXS^uOoTxW$+Ku@3-kL?8w<*#yJ;)!%*xS7<0E}MhQRRa9% zH8fifSp%Q!W!t@&nnqW991zOZf(j?Z2C&nKil6W5Rya+ab)EH4Zck$4NsO$?M*&(* z0SL5vQZv@e(Jns}rI%k~gSa~PN#R_;c--A>=oFsop&c6~37Lz+vRRd%^GgGivZGtoZ+?nXlAD3HWb zm4>dteMl)jffxx_Zfuaw5D2Guarc6lg}<)bABjo^P@49k)0 z5zgVMG#ArQGPCkUTTp^i%VOZpLa0cx+LaH;fmrt~M%iq?J%l zt@{|wq!MYCs&ufWvcapAEL4;OdtYYWdfduOlzCMv$6s2uW673+JH`g}#ngshg-r`H z&z?^n3r0$3MEhPynS6BK{;w|-&Pu_ev>uXM4gf~b%0Wjg8e zSFC>A1dja_3<~!5x9R{rA2Q%bUI|UsPfaahte#LAE?z56&@;G;IMVcb4i0*>{&cF( z8<|}Z!_1i(;AD7QLYakzNh;;O&>S6zU7Z?^;2(sqBK$p!y{Nt-&;t>N*)@XqqZADk z(25+kD>>S|`-0F9U_W5J-+WIH)hn1)8=~1s9`EXQHX&Q4kc>JSqd$RFKsm-8T zJ$s^_*S!Xm*we?oyajXl-FyjLCP=i*!4r}WaScqlN45E{tNmG0GAU1@(RFkJj&WkL%SuEB9q__TT~ zI)Efp+Qs<>^Vpw#;QyB=0gRQ?b?ujjWl8Y zA38qQy!MrsB9|Mw)}oF{?;Bt*6@<&&{8{r}T0n*|yni`x_1_d8`o??l{dy?~tj1^+ zUU0V33rwZkg%QfnzJ6M1YtSW$fqcJCLba1!(o5cfbT84Nja(Y;}Cv!EC zK7SF|7?K6AMLtyY3WH}ys6Kf1hEg77g8?YMP`ux~>fdsSC-OgXeKo zT}Umi$(aActn}-J$J_Np-gd4i4zTEH#`!J+ndi7^Bw!cXA>R|;xW~b+gg`OGP@KJ; zV|wJwUM3HYm~&Pa%(

ul{AFmUY7?oMk!1t*B^uyE{&tcESg*AM?p&RjTsK^tJqiVhKxYuz<}Yok?t z@t7ulac{)QgoW#`Rbyd^!+N60s4>6;05Qym#J}$9iusZg1NW=+ZUw4&z9>JO4O%qU zI{y2Jv3fx;Pt_@5yP$-Q3eW{kx-`Fh%JEruB@3lpv<9Gog?7y#=L>l!iY z9vq3E-~_P)wXfSFt0>{xG9OF70Y=a-cVw6@rcg09Bxb5t#p0ayrY352Y*?^g zp(R5sOGQ2TtW4?!EZ&&TVAN%E(ug8=ZS1t00N8$q_u~dfQi`vADogddxKmjayp+ar z^{Wd^zT4c4bXj`DiCakcHdz91aO2Ul(m9jyYKo&8X$Vw5J|x!&sbkJkSXg-2X#Z_g zoh}!{>$7SwMVSngkRc*x04`$~v;c={<)6rc!%sRaqy!|ke2J)QPJYyS>{qNl3Hc`- zL<$^+dGV!=IH6Zcfk&CdE!qDu&Ck5hIkL=bewJ6~slhEDlt<+tA@fY_k+q=lL-9TQ zJhAy>``cm`>#JkYF3;RKKe^B8R16|@I1IUT8`-B$AW+ifL<)1fVjj?XAYaL|7tAT| zBIPgk-Aa8mACG+5Xg)?9Uw{ismrjhJ=&z1`v|@$Viys-PUN|ZRPup1M)Jz1AP3>E( zRqkRGSWkzo!Mofa149Sm4;hczKhpmCPGF?u0Sr~laORc{`B}Tq5l@lFtCY&Kv(0mF z*Cq~QK8gK;upGSluhuCJ3;#%$eA*j02ASK<@N&K)VXKV|A>koJXIYGY1~+PI*5AX^bD;H>IR@96HF7k}!H)g7$vAH z5`YgI5~xJQO2;!o%6Gb@eGZGHPl{&xff@>x>n2(4amwJ@?GX6Dndh=HIH8|}!aVnU zUhT~65I8<9%qEcT!D0D*6}W!oaI1l=#?Ez?1R+udR4J#G+WW3HC|00YM@=>%}E&fW}gvU=PO$({kqNOBpoOXD#5o*YE)J^W+R*~HVY zz39E3&sm0Nrwv+Z@hIvvDr>pl0cJcn+^Rt5jSL=asoy37Y7r;W;yr;kX9dFN`~7VO zKX6(u9R>It2F#qFO`VI6hoFHAiy*FZR8!;yqI8n6#_pDb3gs9&*5Di^1!>3{a5h?c z(vDhOr`Po92xzVX^PvC4zIYj@>umR;hC!pMtwZEYc2O7Q@59%AY!r8ZGAeG3k{kA6 zGeusmouyZ<2<9t2dHfuKu^H^2d|&;-sq}pOG!@R86Ri|S&=Rl$+&A-5)oR?=cA`ak ze|zR|F6{T+Km)FQ+x>J>pLX&5ZVe-uRS=tQ-5x`UW-7Q9t=cS1?#*V5$_C}1cTvDS z;oe@b3E(1!^%-IBIpARJ{G9-tCx}{fbRP5f*`V=v zzRb06T-<2XD_9kta!zhwBj|qA4wf+f`*v(xVLszRioTrQXFA@~dh z_D7tyA+qTX6GVY6i0u7~#K3l;yJ2(`$6F{KAGbsJ`Fic(@Ss=sfv1|6^-rL%|Iy&r zG(AhELMlwgvyIzk&VPb>Uq6;Q*L8|+S9zMAi=rR7*Q`&a5B;Rcb#VgcL>u?vXCz%a zA5Qn(no{+Xm8|3^5*)D#cWtEd7yq^Vv`DCW4a!61z1HGw(|P!g-*V?d_CG>r&N^$4gd0`i z?)@_-HJc~?;}Z))dxCYFz&ZK=pcs*z$jn<3|JuW#+Rr0)lfvCpA`_k0*}2#MrkWk@ zSWxSm6V^+-m8)Z0T@{ZWWEkQUBaIWkR`?Pm`)=X^sDa{8^0+sQ*7zi0m{3Oo^`X&Y z5|eE8mY2f^sQ-{hEB}Rmk|4MpO+2%--1yTTCbhR`TVxs4o{a_y8yO51ufLznN^&pZ zkMnA>>$El!P%097BISMTXEGMQ|Af`KgkPXZRkTk-$b0^)_%@J=JKNZ_;^&|PF0h;3 z5|G{z5a=>X4XNrEvsD2n4*3Hcffq~GBWOJ+WLS=y|_BY3+4UdpIxfUdDHQNY$A>&Tu6E2cUm1FP4SKbzb^@Jq5 zeE!Fwn}?ytr`1r`=)Sv>Kro#Mr^Y`1@qDKlTNQK_#6_QGmJV)d70{TogYb`TZGVpXqtzD z8Nk}w668VC`)kHD?KH0@>;;SN3A()K@D?@3$yYaa(_2g*jKOz3S8-!jua6l7c1ABE2pTa zci8Xhgk5UE5s- z41F-SCpCsO=~07?fvm-t{88}@x7pVGvF-c-$!tP1OEOQBH)_)3$JQ16e!#*7)Wm~u zPdz=)&%HIHHY!8fZe={&CDmvt#ivz+HI(Pp*b_<5Z!ZrL+!KXWQjH8DBXw`it5diJ zngpwUt=sC<2EXKy*Bz5h0&ST-_E1!#d)Ys!yx%pD4uZ*UYUMgakA-E&Ftl>w3-Amy zu7EJXy|PlMa=dRG!*TJ9PMUO;-w{F!wDLsYvD&lMT4S9%y^R*j3f}VyncOQq|4hmW zS#XkTCCcpFY*~Z59YfaTY>3Sll5=|2-W)Xo#aw3Og)4~}8v!EMolH9?PBja8;PLyK0olOT`?8D-3@aR5IvY@lXep- zH50xbnJsbPmdvm1`MV6r7SXv~w88-w+^u~EIC#CVRkbLYw*jiBe>o1ODt#y2yRGB1 zr{f%r>JaFrK11`I7gEww7 z{qctN6LVD!+n%$DpS35i&T}UXL3QL#vm;ao%C)=7gAY;Zt{aXB10K@b=>kr(wdV)t z#&|v#aX|pxp)Vb|$g?1(^G}Xl6v?}(Y@K4Q)9X`b<30vu9$H_}!0i(tC+Y2NwSiPp z`39T37d>5dL@9w((l9fGa zo+ew?bt1rzWDy>pe;aA&$bVt>m|WP)cIk{3&Kcdg>pHv~${b#j)pEN+it z&W}fB!?K1m97Q0AF>5EqEK0F#TB>>I=lI8yoB#ciNut8ye4FmPV1YqF`e-&ZncQ$f zXBj?aJok?WTW73O@ko}FNF-mK*-@DlMY?b%=Uv=ig;#p3Ak#k2<5w187X@NEPNqx9 z9(1pnhC+aU-*jT@qNdSP-JOMII`+A&3~9`A4QMsj`51$`{SIG%6 zu_(RHLyDpGbGwE(UnUGt{3rESFqdg}!Ift2V7`}3Su({z=lR|?6do3!2J!_M+{55G z=Wah+E>9L;aI_=Fl1?Sg6`Dmmr<2(ZxL!1aHYo&dL(OmJ$fzMO1<)4)S+qO-N3i~&BTpw5K@`*U~&OsjW-h|!> zm7u#BGp(<13}jTZG6QrzqrX^no6@)Qv-nx#&My5-I9&yhWk%R%M>y*t_e0?u*TA^n zmgegu{MN`#CtULz>{F^|)r{4EptCN>gzxGk88gAqpZb3J|@wR}^$4%zHk?*_`1TdI+s{t~dDlmnPzP z;F#exTQg0l9=`U}NKl}?ymd;i-oHtuEu1m0< ze5R(AjJa~ANm7Ywi3lnh+vrtKCgioK9OpMX;Fof{l@C%MyOwu~%p0iT>wo>FL@Txi zR#NpRuVAuBJniPRpxT`c5o%_-2(ol_xOF2IDFWu!u68RW?@45l?`(f+f_5~N2jlBC z;{`L2<1M%$i*|r|5j-R{Y#`}v5^42r2dRqekGzw!dabEEDE>31kZTLUg7MF*`tIjF zFFVwnTCB}?H~;9=e79pmK;Gna6-8NZ5&scIp6BL)_ohwDRmccmEI-5zM(MB{Qd)X0 zuo0LX?4=>JO#Xn}oBT>JJ2?SgV8@|owjOaqz8?!ju36P0$yr;Fyoan}DHO47985PN zQ2#+<9pd>W_oC=o$<4^p@|qk$djTKsxi+;#iMjYi74E8~*}mF6Bg-fEAJ8O3b-l<` zL3)=f#UCZzyIIr#tux-axR9Zv4=GcT9*qN5Cx1QC9Rqqgith3B0dK8i)Pcc#hor( z+nhPGi~kuSur8CFD)NQdV6nrTc09ifqAiN&V}kZ1y?TG24pvmELthCF*M-=}`)?PS=luAOgxJLuSfTlnZMyF*%tybdw{KIc zj`EWyMI~_xCY=^ytXO3~cMJ_%yl8$PF?Ya;3b9wysdQhfrffJw* z+zhkVgUAJvX4y8inc{UHOy0THi3|dnib~Di8sJlHmNX=2zC%&w500Yn<`*@PIo@%GvNL$iyW~h^&m2hmyt`97a%qQ*Bt_?OkB+J#e>R>E759Z?T7=!p0Qu+$+XZRdvG*)biy(;f2$#I!r3#rLZJ3VQ?T`Qi1{Pk zn#O{L`rx0Nr(K%^_pf)c*kOQbBsW4`(!3jV*Qm=IX3Z%GX*wkC$!2!N4e*!D^NzQO zh74hnJAev9qle!S$KNXpBTpxUw<9NycX9BT%uNe-6D7aRG)R7cuzv*KYDvS`U?5<& z@kTrLNJq;2li6Btd)F56DZWqM&CAZ>Ix7&0oe=nGmOi(SMrf(M+PuU)4*I6Utg1Ln zeXswP*|dFD3M=fez~`B(^5m^wH3;nTWtnADd?9HCJ9o+ zDjt6ePYfNdE2M7mWs31wVh$*5YvjuhN`c5&!SCRPS13g$%a&8T?cY8)+wln4{IPs6 zxc-ow4*I**lah{j%!?Y1Ua`&a5a z?anXgyFPLl1l@E@e#<52`QTgDt30<(Yh*p<$MY0_93iinXZo(uGF*RQa#G+&g>`l_ z1UEvL!N{;d3dy!0gw(cgJ&Poo&-Hyq@`S;JPkEG*M>Y;$!iE4XMdNPf!GG&a-86v+SlDyrPg>P^eX(8s!H`?JEw)5lvm37`> zO>Aqp7Yju?D4hU;AW{XT6Pk($5=A;8^d^LkQWAQbzxRF1)dn*tl4I!&5q)2+tai~a-2|eXu15DsaO+FH z{%p2Ob5!Q@rwrg2EmOvYO;eL}&cZ7~F)2>W&~o*5mr&tbUrO4(vnhSd)l^#&oju>r zl0{1VF|o>*)U5r>yY*qn571G0n-;aJ)f^M3x*}RCvI{AaX`5C8@EJMsg2dv4+PAzg zWByN<2VMg4GE^(k7Ilo*?n5byLd`Z~Es8xA#_CXEj^Bt$1^tx>(bZah4Mt;m8s8no zKEzUK(_2Hdsar9%_j2p>R!GALxQpj=w#?<-H=MHl$78;qo%y>@6lVL64Yt+aR%PUK z?zUK}wRjI@W8BV9*O%l)u0$E=ooAq3zT5Kg7s6PA z_}3UM?7Hv#R2o^eR(4gO1r&@k%Gdo;gQ`0AiwL z3G47eHG|{c3Wi_fGpU?#4syo1b;-^}(kmYSrKM+#Np^C&zXV#{?4>)~gEm-Q4V|RM zFWsPxlW27;Z{|f68uVD7eM@tzW~IRmKPdm@!tbH>X;*|jc_a~T&AM4LB;cTBRH7th z(Lbe~N4Xc!)n5g!Xzgn#PAbmZfX?tcutIKO=fkCIYr6x3p0wUjTgt3S>wHQxTd!Lw zq%4C3@rtRY$~Yug+_voQ(|&7I5Y-a@l}L6+p{eQ@QU~c*f0T@?aWnPcd|KjPs2oBi zQ7lS)2ISbkh4bJNY_@foqtSO395L1(-I8>8i*}i~8Q1UE$});W~QSFb4iTLV*wt!mxFMO%9Wtbk#xk!ySNq$kkTV{%k0RTG{VeE0~D;hX78jF!N)c7V*O~( z=cDLT#KmW4{LF6q>mBOurDL`ErxZfxBcvSKOta}I1U=4OE$^fTs{edtv?h%e1 zE4T50%%h3P=*@&20|krea&5ZI_)m9#WxcIWc+M?Kk|_RjMO-CMSpgw3}( z=`%AbQuzgDkI3i^8Du59Dft$L|3LK03uQpp!XEy&8jMA+y9*Y<6PJy*ckN6!+9!sJ-M4Pa@EJ)lPX$WHo*h8glCXwD{vE6-cX} z%)C>iiAbbMZOS<=C137(k7(Q>+AMBxspc2uncC!)=& zKIN7B5(49M#I+xt^U}%&Bgo|6{3IZa|9@m|>WSC2y4s8R12<RF1eOGHMxca1ziF^E2ElJ_sUZ;1uvW`VCuUj5x`MmyglCrg{VjSxav>^EFxQ6;p}>XpKv_bD)_ZwA#kv?p z(B>>$gCRsBkJod{by=D`+*{MbtI7QQB}Ltk%t={0mS7GXoCdF!45>*Km)*;3N@Lqw z`PwV?V5^CN4`I@$t~=*mCLw~iraEGgb8NqV^T;}nT<&KFJvmFceZlh7CxWQ6C&}O< z=SDt1T;oDqFZ`55YD@UkL9`mv`Xm6#BEZlv8)AC5jfoe8~R+Jy{G_{IuASq#Z5by zOOYHD5*}eYFt!=B?82??LDyCo)%YdCg+8Qd^rY#-o!&nsw0g;l8!;wJDNb~G4n8j? zW*{fN3;}e4v>6^0qP*>2P*@r>`Bvc&8xK;3MW>R3*nETq;NfJ#(qLdhUlB4{6wK*n zRo%cPncoIjtESvFUi{qQ-pbf6LJ0gwa$rhh4SB-&2g|Lg9p#v?NNeWbVTN{_)mMKs zD}o<8NZ+N)iB^{}ac}o$(~U!g33S>_l(%YoO$ z=Dv=jq}sHm{Q5l{(P`+|@G+xK{3o<S)vnCVCT-uZYjQeWA7aBjr8m3L z3L0|`n*z4b{4H1xr=-xSNg=C6p^1oAst|=^-YcCV>L%5ZZ`q6Wl;dM;J<<`Q54&CD{5n^4$)j> zUMO|DsGvu#j0fI|9fT@@9qA(bSd-v-jp=O;78*MJG)4=`%C^2-@K^Ea`8;JX(4u%J zgca+BYo1pY1QgahvS+FL3l2ka*4NUj7nUn}|D2jYSXFbwvffPQ-jEvp0yVzh96Cj1 zN7Z<;YQJ{ny0DnJ)m6G%`U>~@q-7YiYY<<;id=!O=T;^h@(6k7XLSl4 z8%LnP16-~ztz5Z;oB*q!XW_Qv$(7@1YWw*<)|!>oaRuOgfBTFl@&_rKcx#DejNA`S zsb>)V>_EIW_o9kY*m(tgyX^pN>oTCfn9&e)M%DynA=ZLrvZ?e0?e{cv@PjDl;||;L z!7OFaB#_1x))V*ozYaoI{A8HLQ~TuF^l^n&eY%*`6VFNb*g^}W1}U?;j$@AP*z*b@ zvDn+-sf)dvA9@5Iy(hQ3A|H2N4hG3~WXYD?#V)*#6UH5P@F2%0{bolHS_9Rxc1n_# zl!1otbU0dN2f)4bZ!|EZ1Mhyiy11@p2+(Q?#K3yLbbH!#B;b0Co#M2w!lf}MoC9b% z_-8go{E7+;|A4Xo1RrC>HJ!;bfl{!_E(;HjwOtfXV5>N`QFd+N@ezfOh9tL_oZXp( zdydD&yzl~Sc=!fTtkFSXVnR09@e|J^GZB?0BZvc^)&J!*{c@>iBxS|MM!dUl>odXle~v1z|9Q9lOe>SJz)X*(Snjq zMb(5DCm%<`W3gSQ~Ir{XW#a` zHJ^5vHyP%(?>drv`C8?#Dqrz?<6E-%`^?(r|CKE(8o#mLhzD>pkcF%{9XF~pO6+@R z_{ZqslVbhMN=)_2)&NbG9oyEy6G9&~qlIXcd$za@79a&*Kp2n@PJwB?)-&bmrZV>0t#K`<$d)y96Ndv2F~lA-DNo>r37aGs;+HeBwO?#9T^jja6NDqQ@xSta18Qav;h zz)4>>Q~@g=irl%w+F`U%2AH03$rfRw!AoT#!GLiV=E6xuy}ZY^2?TUlrO2sk;42NYje4ff$2TloaVr(bwc^<;9QM6lx}D?x1W$HD#4Y(9}J ztHI`C2_qpj}Aa0IhD4)BHoE(qo=TT$rD%jTn&`9f9VOcx1wfD2%$%dMhx;2Kyy!U7f=z&n);H9k2yb$$Gk1N3TS==4(P zP}MznHGbijg{7z|if8qUVj{1qIKC?d$ZP zYOVd7a|U$JmDg-X&OU!*Vz0ij-kAk8ky!dN7M7FL-S#gXG@#+&uHU988hubKabed( z7UBG`1Gp7NRx2C>1r4qxfanOW+i;DpL`Aj`y1Z!x+Ww|{I z`SmsPN+B)Gl4?bZ==?xzm~6(enE1jZKscy zb|Bk-bWaKP)(wxChVl)j#nw*jZln{V`Pe@^QWQ(Ix>PLnk@CKN+kgm<8N6TEOCf%; zwN8Iy9KxSn%y= zs9^n95rny3)jK^t#L>rPss{|@fggdN+r1XuRrVwb|9#kS8pD??1D#!<4aoPIHyFC2 zXV^blAMwR9AL`oIV$1(Hw1sp3`8fYS1g_t!s{mV{PpJG0X(vnu8Zwz{pdGF8vQP~? z)j8Z4tH~78ksqEBz69MnO0v(`#!@sr!ORJk#hQijI?Tay!UWbN$z;*b|2Z%L$p_zc z5QkIxAHHlNSEk}L63}XB8S>Jg0lKMSVwODr6Ta*oS>p#{!5jwbK^d1t8jg~8>g5qN z4ac4yNb$5_7ha;*c_S|O<~9ZYQhH^ycF&>VYvpQZTPEy#tjNjbBTL*Nwu3WMK2;=~ zgMSgcTYIl=`|W}Xgs~AWh2?DM%PdFds*Kb5=r6k7FgN)5^2g;_LP70!P1=(pQ;~4` z0;UZFmI2!#>-PHUM@-y>oPqd2IsEKwuo2!A7aFBHA~3Q(w&jjF zujobEyHCu6#H&|dIAFH!Q?8`IQcZoS?k}|u=Zz73{FkkPqa;U!-!YNgal@?oyUGE_ zUau(^_K?WPk(2&dRPBDo-yHI62gG~V5qP!>W1@WkzSy`WzsT~*#*+i!*evh}$Lx(m z0Zbd93aZIu38sv(IWHT6O;fTp@34aA3;mSPH8> zkexvZ0r1Lzl;fZj278Y#gJD0PPSI~X_`Yy&*W=`ET(bVw1*_s1oiJg3Tu%fRmf0|& zWCj4RGyDI*pg(nL-aN9`)*k&(@)pl3d+*cM&m7!9XUXhS^I`PDQKfL6V>X;2;35}L z!24OF*Ufw_ar=j?QBQS)E)Sa^v!6e6x25mjz~yldz$wgD)vi|&Y71}eM!#c(U2xGC zsboK~Sbtz+xoLdr5Isu(kkXD9yF_9S{7+WueL7TO8hcYfz&S-s1Hh4-{&ob=(we-y zYFv*)o;TrH%IStxAg}?t4hWe*($KxHBP{A*+=BiR;DE;njFk{M5F?0p1Q^>w`{l}+ z_oM+A^!AXi!o7n#e=ZQ~`npc7JdK0jVj&@eO>YbKYMrJW`#X4s5No!ql@z7Yj)dlK zK6R5tDNWL>UwY<@sE;Et*G9VBG<`gAh%RHj*cc`QA|LH1McjZ$(4nDVFM#iE60mm) zeuKEcQ&_#%%e-yN`(yJSGULli5woO54BiJiKBY{&WmS`#Z|JP#99PLQ zgKOo7rTMZG``!r%Wl69Ycg?v zDYWHFAo9qY!k@YXLvwyvc5mEu9W55!E04cmRCOzkhs$cUbXe_O)0nm9XMo`NBgaFf zUQjYN#A@(%z@Z&+PdEEn_1>@S+*)9Kz!w3jkC45|L(vpD&_tgGToY}|ar6DA_$X!B zwO3j^L_PrFaF#720nEVdJ`p!1pCwqEhylM1i>+?3r<;2%+i9o{M!4;effXvSV zkZ8*efEvAXUwfS*B?HVk*1r+c&gwO-d?pZnhG?Xi?*erFNnxJ6m$*ELXE1)`{OLR< zMImK)^iN-*-*{#LtbH7GBW{na;9DV#*w*3odl~JzeZ) z3DbDX7jg%KuSXVW8@@?kKhWArN#y}WN12aU%Y53*| zyz>*E07AX;1Lq`{or)7CbL<~@0l|lIi9mA3(954UD4SAbtFL5N4u?N*W?(Xpy}ZsI zpKm7h*lOx91VZMxzS@`-SepstmT2Z`@WB<<8#V5H2_>b^YmP-elR?W9+<1%jeq`G8qW8s(*UKTJy!Wu@y@p(66aC%y9i6vJtRHzS#RP1^# zJM8XW8F=M7`xOFW`72kceCr3PcH9b@19PZ$i^~x>XWcUUB%E%$i9s#L=P%YiTyYmo1sWY^6@}RlV4Bg?Iz~7b{^D*x-g1OAL(@t%d^%gN-cksURE{&vq?a$ z!75#Oq2-PZIUJsa-lv|lV$RQW4D|FDmQy!%?Q^lUJbN&1`OjdEXi3u6_y21g&|zFO zJ1wUN>mzVYJ#O>J-;5yr8C9;o)WTMZOs)TDO#6eg6K=70X4l@)=pa&}n0J1Tx}n6A z)5Qo?vHE1Krgzu8=jB8G(%5UbSUw&8-M9}QqSj)M6Pn3Yi#}K<#9`VU9*z+F9ahaq69tU3!o4PAA`FZUoK^pB17Wn3}R5rWks)e;;0!kAs zafW_>7}517ceIJiu=DyeJm}e_(Wm-ia{Z@4^K*nXb?waLjh2=wa6xC(Ri!%$2Ecf$ z2v3FIG30F=EOX*RHBPO4Ye-4Gr(5h)7m{ZFCDQJu|0kJd)exX2^~IPNs`8 z@mnLY{+|2f#NX$fbj1E`fI}@z%Z+C$kcoS5DiVd8>>4=Q_X;ARXZ@Ld^jz@%#E*%T z%|$*~Nk(Ux9Zm+HC-^8Xs+R}%3#RFTJ*+dTVO**kprP|AaMXOeY9E-oxHwuk&!I2> ze28$4GxW37e`fLDCtihobA4g3iip0-9)ENQTY4u1nLe!{4c|ANp0>s2#US#neDV<) z9UtZO5r5U3B(xXaPkMd#pc8GZ)&EKA@)-EaOZuf3L=ZnC4aO#Sd9hTPSJ$?B$-V6@ zMZOMiNkjXtvi?(JGd-LUFnpcI_13fIMHBZu?eB#KJB0sy{`V@wNAu}wx@#TF$^31V zezJc)G`>kv@Ht8GSc}}y=)T-SfrggXeWi+W~jtnzOz9YjsQFCak8U2IoofiSSUs=lfBjiJFO zPlLp7ay%o|$!xjag(e(kZZ}UojXI?6@5#j)z>XBBx?CZd=FCDzA`a`w)tXM3&^R5# zyLDdR$*kCQn&_kXcYMK=Q{3l?a$bOB%w7WYX7sNO)o33!*pF_abcv#o8H&qAVe_n> z^TngOB=Rx$Z-+)nvSO-2BMuujM^}B+@n^98PoP}y6ElM(#kwh-qOeXpWHD}}CgMnB zGMaa+wX3Fk+|$T2Uj&l2sHM}foeVj$S*&bcI6a>1obxa1kXxR9doV%nucY*r%A^R2 zbKTu;>Jsfx@!)v(PjwIwcVEBi%`k1%B}akE$1_UhO;WHSk73q!c3(&aQk+~^!m{$- zO|O#6o=;F3A!{F+ixj7RT==MEUPAfs*2m|y>QjHxHrN%fcUX_!^Z#c({1SG3f4!2f zY%FukqzBd2wE1i6H@0nhRu6hFnmgH-LO+pNKs~$e_+dBP+ZKxbzMWZCCQe2{5%45< zO5FB2w~cB1F>gQTKR2W+*WaktKWR?{US(R8d)bz#Gf%EYfh()UN#Ro7#Vx*G+ZRgPMki8HGNHP1ZEHIv+$? zqtmZl-V#i&jC^G^9sGHHeNKh_1l7+`n)IONQpLy{zb9Ey-tSKt=5fDL$ww3Mje)P@ zs@wKd%?@xUvKHw0ax5$tq3C}CwJ&IXd=ORJ%H;2Sxvzm%Wb%Q)2nH!>>83R0@W!1T z$Cb6Uo0F51vmUp&`Lt3yH_!u83K-b%e|CicEfn5uL%h~4$bI} z7MSP@7s~{_X61UKW);WFH}EUh?{j<;(EjXtx390ipN5Hv>9bF6ZZ7v@yK(J@p62Nq z_S2Qr>Zi{4yMxs4aAI*5UX}Obuekm10pRbYV?4ei&ujaP(bGDBV;>%?o#Lm9SE*B0Jw0ajr txp>=KXHIFka7B+7#e7pWPLTBcTB}ChIOupS`3mr-@X<;`+4?$_TFo~XPqc54JC3CMiKx3K(3;!pmXz-y;=8&2yX5> zA#*eU0GYCbyu6l*ygW$D!}W=S6A}PWj!J$^XsFvmn{A?_Vjo1LO#CH^T{-m@A{qqJ zub@tpMMR0-jhv>|ZmEtYnjY4tR-D4=HvX8Z`0*qHKRMa^qow?+I?2Y?$^7~J@22{b zX1l@Pnmw}_3;?fEUmXXEQc~G+PEA@m)_%r}#9nqdkmzfmLum2j z$wx9*Jn5aVYI)B3^}7w?P!DN zDz@`I4aYPl!y!6R4pcrWqxm+V$%xYs!`#XU`ob49)KQMl#*@J7U$cSS?d3S;%AD;* zR1qp3dHG^zhh*;bbk=oNx9`lEndo)DK~>Y?yio*Wip0{_XqFSd-U9sk9qEV zi*h2r7D|Z64qex1CB>HwGUTsCzskEi8J@;B6dR|9wUh{B*YIkNc|={@zd&GZ@rDy- zI1s1aA0O7?u!F4sdFA&pj9paHI7Hx=0x>mXcGmN3{s4~1jL=&sYneDLX^GNi+8_~5 zJu@kk5wFVlcyzVeui#~|rVoXXkBrYU`TL073psU2d5^`BQ z+1VXTcis&Wf&torxCj6#@1io{D>+)KT9i1dh3DuI{UVT|8xOIVH*)xl^W789eMU-> z77Hrkpyyw~hT;NvzqPKBvhSK20?8(vntC~yU||pF6oQ#g%d~t|2=cgsc(gdK_@HcS zuW=(he%P@vIp&EmD$0P>iWd^;Rmtu?q-u+dts`a)JpZn}&xjYn^dsi{(C&O7dp~LT zAzGnM!=7h0n^QRPQj3!GCBd!;BCTlcaPMj7F6bR0>&tU_|L&Ok?zb0%;{p?=(V&;R zz-ngowcf3Ol`AFk1#dGOCHKPIB)KHei?+Dz8I2iMT*2OK|Ao8W<(s&eRkHpI`kY^8 z#rXTIzw^0jsIU=PEwMK174n80mR3q1xp&x6hEaqDBey5`x8i7vdwH0CMh3j-8f(`> z>HIKWpV>S!f~WEbYWcGP?JB)qKg#6mwfXox)uMYz^;ABhV%Bud6sUC-_f|&NHLdiT zFx2-dqkKaeaK(qgU?Q3}^A?{qTtfik<*v|kC}2Yg@IWf(L;UJH@4BA|fL<={0Zy~5)a3XB{YCcRv z5wyH0RtFFc*N@y08XDMvn0l@{Q|DAwHpJfYTuVB8G z^hLGBTb;M=5$h6jg?h9av;tfCP9?ml=Bc9;xJR-#@E1C1tZCh$?xOB2?ve-eA7f6_ zrsdfaUaAao2I!DQDfMzB$4@4r5@Qp~A}r z_l(dv{8-Dmyhip}4JsKGa(rhu6-vWm!csG+kcG(d$ihHVy&Amu8c+?)X4yXk=lJJB z8YI1+9n$-?9a$fG9MNv?4oelEnC29?7PFOthryEzWdVq5QCu6t`wz&ZZCGtcmud3b z0_`nbzlwL?2kNs@6vvPC`fQD@pCaU)lc-h!tU zEtbtK7cGS$ClpOKFJ42_JJU5J=bZdTs=E4T1!o^Q)=ch%8l^(UVBN63=gGgRe`%10 zD+Y#5TPJsDN6Q$63rYw?=(j+7wra$xUsmWDx>Pzy6X*k#1tui4w(*-hM~ofe;g*Gg8d&(O_GeOvI%mBNEQ za)0Yyx2EiMi0Vg~uA{#Zd;fI11<{9?c|6R5XLSs2XJW&t!cWN($VwPI#=_QGQ9V8- zp1u!~AYzX8Bg3667sS;}RekMHMwA84~^gw!9*mClye zkIl8s+BHhnH#2^RAs$#?Mw+ma#f`9%!i-@}Xg}Xx*fw11i__=P&!t~n{Fu;Pe&A#2 zZTWrT+7#da+7kwx$otMrek*mk2Q|_ET=4u_JbBrm@Nh$4Su8&2F+ zJCsY)H+*7fX6RF=bb7dNLme8~9l1&^S^vaTx;6z1?|nMnug$~ZkZ_QYoDi3nnP;m# zkUuh#|L_Ad20SBSd~1##*Sbzrz~)ESOqWK~C5FuX(N0>asOEBb*FdDy?V-pVnr4nG zGlW~~XlP>;MbwM-6wa)I1C?r(y;t&yk2!1OSR_zu)1-Xdd`n41dOD6eTa)A2?r)Y2 z;)Gt$RIImlDHvTk(tW={RRPr5X`{B+(?kR{cFcV&@fdzGQ6vvD+s{1DW%W3q@KaiBqm^mAN zd3$yVZD|nL4w;;C6~SuNd>?yw&}ovA_2zRu1e*dbiT5#Ek znZ;HPJ+rv<$6ihl(i5sO#fLkP&&A|*9v3AQ)r90z)QFvnvz=l#_OKL2tff#VG0UV8=CEV;oet}(#X@9U5E1M@0rw1C?3qFkismHo%fG?y0W9p`UUsd z|9tYhlQf%-QP|HEwja^OMraH-VG{N=b8Oi0tgm;r#U=;@J&v^?ulGA+JedjG9+|?r zaL(6xdtMA2n*^H-xvtOpd-Ggt?9D+=h)z`Zw&%eCmS?$Z7O~eeb3eZMpIUXdMaM0% z&0+cjE|#J$de&o?iVurdhXk`Hqu1jL)eibDW(2GMGj-l#0?cCm<63HC zFM7_VQOdl>{OF7MMd#^2O)bZK&0+g744ryjeuCK~T&Bdz_yxdz@%goF|=8N_DDfh@sVs z;sG4(7tNM?#sVt{DH##ss^%#*%vb{dW1&;i;2OGJwu~fQ2mv z^JV+&tjQ^;XP#hjn&#-Y4xa*AVw%1{VJc?ye3`Pl8Thax5Wf>?4Z8WYAa+wW@&o{A zx&ADmiVo*K0Dyzzpl9f1sQw6Q{ zoc%8Z^k)CZ3}y%Y1@U?cXE#*W0?E62AVK27V!|Tq(j*`d2As0`Mzk~d590jDOjfaDq zmxHSd=uccLYgcbCI6M2FME}12)`>(r{3nx(=fBFjDG>a}0~Qq)0smh#FNY`p5ABcV zZ`xmV{hbc>Cm2-A0gZGrQgCoax_I75lNNsf`zyjK@6hwzZ8r@sW^f?y5k&nMpNWm*Tv#?MD2Pf+G#;mc@2lQ2XJ9Y)rg?d$9ovOug+K-Fd zg0^}++_%pb>5Gci%T|G~ZxTy5$D#92+ooq^Uec{8mlni0Wv<=k3kLX(1 zW#EhH(!V2K2vA_Bc5-qe;@1;pR^if~#peHYhf^PFHd_7t4XNX9- z%9gptg-Tga1(ubSSzB8(qn@!|=C$R-&z^^VDXyt805sHA5l5YW2aZ%D$61_Y3m4+b z7r@qjPYAa4P|&wONeDvhpFS0T^KFn_S6BCKX{joDd@yk>K${T<)|k+NOroJ9B^Ogy zYu{-dO{|-m{V6s%nYSj+>B=V{)ZyBEm55;bm8S}~K!Z99UI<{)`7u*JN#x z+RJ`JRT0f#OF1i$XcTT?yPvmus@A2wagbKqUr;c50t_(QZ0YVM`q}Nq-4c6@I=yTP z<^N2=v3+~0BvZs~M>}0&?H2b+({@{0{hgXgkF*vwg2kZZ*7Qk0`rw7e<^2=Bwr;aj zVJp-zZCGFy!je?8x(Y<~miE>TDw6~vFzi4wz};Gs`<1+SEFB@^d7~3u^WGV&D|3E9 znu)#?mwRqwvwV6u3t<;m2|fts9wbVnQ1HZEJd>Z1GusO+FG!ZPAEDv(_@AoY3!r&u4U?junM_>3;Q zeRM>)csEQ*>8X}au0%q^>x>L45^@k@jE?etBgC^v#788a3omzwPP62>roOH*VMSiF zU&s0|GoHd5et2>W$2{(>z)A|OEubkt<#8&bTI&*V90LMz<#OEpY0xy$LG75O5D?l% z-9I!Gtr~r2ji$RqE%++{X`)N=Rf#Pi*xdNY_lx;U&H45SwoFAOrA9!g&9%o#4h|WC zoSW=VuUT9c+V7RGyI>cmcfI?pE{#-yr(4^uBJ>U6XCX24P1HDcVUv?~c+|&-1P2$M zEcUQjPJ<9`h?ZdZ=XS0Zfw{CdtKN!=immxSf*$wQCgJRFG%-%|YG788H~^Hd!^YB5 zo|dpzH4l;tN$8I)XyC(NbhIZLyDd*YT)hIWNUURIVstw@WT2s;rDEvp$KLH8;{M#Z zi^|xu)6sEYyf`Q(C5mWs8?N+5dh53bsDpCHkz8+HSM3Rlerx`alhWo%X$cWz>sI2v zZ`8hDUG{5lbkr?GMJtrL=aXd56+uFhMxpdAK;d0WL5z_=erp-ppimBu%ZCqoM<%vO zm!4|C&6ebC?dMl144}bz8RQKFEvFNdkp`~H%kpq-`vqnbye9?t1{SKslWO~m+woDx zBSix8mN9MSXOosC?<+l6TF%3K#}2P#@x^>~c{OJY zU#`usUsy7+?Lhg?G{;}ZN7wXCMO`xt7j52l7nVF`Y&ljyXCovXPxSL<_9<^)1BpYg Vd=vCFEB<_cRTMQ8$`O{q{{!FVm_x1$ek}v_@?G89;!Uh0H zRP5#DwN>TiS+(6=Uf4U@001gcsn79YPY0=yM!KqY!2~LVpQG4R((lQ|u(Cd@qDYpJ zixPSeiKfu$tdAi;qn=SH&S4K2R;MdgpGM%Org~MI%YV}(+S)l?{=IzO)_mG-J9hqL za50Mx;92UcYfn~6EK|YpgqntVggz^Ihz){8&=Dk7b>{-yW;_%h7l*BVad4C3Bc3Ok zQYN5Qk-K?QwnZ4`4h5+2_iSTJO4F=e0aklomGIvM-uvcQUUHsUN4mRA!&`#zeIBFe#kIt94dfyCnMslYZ>;pizMk5F~b zFA%vnCUK*sv22nVel098K8ATh%2QT~fS^&B@bgaw@|L;++*{GMd9mD+@ImyNuVws;$rv_85rF^)uZRF``vJJ zVf(@WlFr4i9l(NRTjQCjkcOs7%%%|UVIY)|OXB7rQ#=1e8h#c3%IeN28BzD3F)2cY>j(XLm?bx$`{kpY-iZPgL?bRzHD6v`W^EJ#7-X%u>RbZsgx*4Ho2v6tRRrS?- zefNY3pAtR{bMMmc!s_BV6Z0ZprifDDoIq~juJln_QoDiNgxr|i#E)pJTfp1@#zOsMi`)d2uG+LlH zZB0Gu9Rc?gw>pmz_h^cG3Yi-4S%SlpU&Wl-wI4i6sHXjPcy=H=438c?;(NsMQOMBp zqog5~p?}?&17!L_WvWT=N2{>_f8y!3@A1Q9!wbR-oC|!X z@DpvPiUt|~2Jckw&=actbPy$z5mUpMLXKRHdkzAW?%CqW)8gI2XoCFCzr?!~+9K}d ze@yGw{mb&${TKD_K1!8ln2V)2;o@49!rowt(dKd*C`9SgY3** zIz$JAxgVo#P!1@k4=xg2f`e5ZRYQkW7E<@E7KEBd7&mk`OgBh3ie+DfqC>+%sYy#& zJZ(_^1)WN=N^%9d1xreEaZtM2SoyfxxO4__`W5j`&1{Xn3=L5O7x$sUmsOqS?VXpM z??X??+N`28L2vusYKbp7`c2gJk1X;pYB)5^?u8koOHP3Yz{9Un&nbRt5r-=Vy+&K6 z_Ugn)8-(+V@kKoA1P$&qh}6ec>A{?99P9V$YZ}$+cxx7%yjC(D_MLJpJ`c6@wqW|Y zUet|}WP!4z8YqoijFR^0F^?M#_V@Oa_o>mM3y?q|A>ql} zeUE|7g34kS^M4pkN-sLWY~Pp+~6>H^_0RDL7}}VIfegKz9?{`qw@*4sN=-`0&(62j87-KYC{U_o zL;x4W4DT(`;#f8b@mYQEU+CA0xfZNKe;6cV~7Q>Gp12KVg^lK&Z|7 zGLG=%J`rbjmYuMW?b;Vr&>Q%hllK&p$y45ih>hMu2RLMV@p$Lh85+?Zej`WD0eiSb zc|rV~AlK&1wtN7N+|F$lu6;_$%}e7ICAp?{R8}5YPHJ#aYgN-|bNY>Ab8qb7X3;n1 zlr8m|hg@7)PXsa+Ila=-R4~P7S_Y8!M$|kQUgfX%ziRs8xpoKWe96nGglDiMnx)=Y zI806>aQ$$TLt>_~iymd3lna(0&TXH0ULU8?r9IvlgG;=DcuetI>tB?o&Ck}x*!qkR z=GGzvyqr%KrK62w^eI2*q=PG)(dBThqxJJIKX=vY)U6+i)0{m*SCN}>o1$9=5EBcE zX6m@_H;0XfhlZiR4IuPp_|S|uVB09Uy3ng+bMn`4+=kccV zRnhgOo->%4H~P7JEIMr#q+W5Bn*NGiqf4H~;b++*B zhR)8p2x7DwzDy|{^%-S#iHlC7XHr}^oyS%#J=G`E9=H457`Dz>znq^1VmL4hjr~s2 z2D{IUTDv{_CqZ>uI&;k)mt(`Na^9jdtKb@ZU5hH2n z1^kS`hY|fO_=XT81_56ahn78$=4K~rOcG!4^LR7TX1@#i(}mZ&6LT16j^!pVkIT^$ zqY$HUm(9fhFRmM{gC)sRf>X7F-DO~)`9^mE6Xk=e*IPN(C!_$9PoFcaI*Y9Ga{Q|*1dCsS5mrHV0bNSjN0_?Bp&wrVk zIh*CCaIKd#VAC?%Dd7Ps8#@tlM1a^~*Be1C#Mo29d}vlF`PmZ~f?6+%3-If(XtBa0 z9;*tUtW`3R0m|37LnsUI@?oK+PqJ-lEortp?2$i1&7Jm<0CXP%%&ZZJ&$|~FZH~c% z%Xq73%3tTYJPL3zG;N{6T-@aE^}7S@SW3M?xP3O3thbW|p{t642LM3*@DE|B>T(GY0y1oBl z1KC*rQt^BVVS{OEv&y@;+pvlXhzJO>L5WydS;6ksFF?8qO8a&b{cj`xYe&Jx!^+*>)zjX^ne~rd z3riO-PY4^^A4mUQf5&M9xBrhPXODlSb(VD=wmsa&(Lll8$;R2^HZ-W1F!(Po|0VcOoc{pA{sR;j`6uunf`0)2!~uHZZf|p2 zqCbUz3W0(D#ru~&82G13|ESvEE%}Rk+Y=}e82Io0LW%T<-rmljxY()+vU+y7`-Ym1 zMvCOuj?(=o2`_nFJzgmld-Zd5-TGAe32Jwl4=N}eIZef0LS6}1xyY9f6kSWB!@^dB zWC$Jv#DD3*vQxL0W0Y~eH^FKDKC_9JyE?1T{qi^ZEgYF^#uTNpJl6w%=8i49`)Cf5E~^_##%KI=GjLT( z+!Cu^URmLiE28;_cu9(g0+HA5CQmJX2ysh9Ktjkov+B`%i z8J#gG(2W#O=k{5cuXwY9Y%DHoG)mUDJYHb9lrCfl+BF#_B^4Jjwq;+vND=dWTFKb! zP^T8Z@XZ)kqr)zci+y$EZEd6pV{Kv+?t*9sc3OGU6X+EQ0`VlTxRrP_0O~>qrS^*> zd=4Onbsf#jt*oW40}IM*#X&yc$TsNY;Cf17BtNcI63l35~LNdaM zpRo8vi)Ia4Pj~$yz5XQf`Yl5(e7iS*5!{s9idvox$N7ENHS?7LlPsV4wyQEn$YB!u zo;;AB-_p*G))sh)XRV8F^%0LhIW5B-F^|aELDPVebjr|F9e0AXn7C2zGL>^G22S^n z;OTc4Qj~^8B(XnGjnptgeirfPJ{76QCFyrGCE}jqWq)x_!pP>3=7sC3=%Sukk!KL0 znySYnd5X0wQ%&@iw4;o++-q2F%WK3C z0DNKq)Gf)9xVpxdkaW$*hMisSH@OUd&d}G(-1#xCIvOa7&p!qCb|x#<%IWhzXbVMr zPIxD?Qk}V0)Z+SNbi5!>MC%<4)>bkdJ9W?Or<1DVmo1f)PU!L}hj25tyYKy>Ipxk{ z);hQQu|5L3aKXZg87b1J%$KkWGzJrMbVO)crBX{J`v_IIEyEfVAFraA z^gULr;~h!~b- z0!-BxP!s9l;a;&jhRO4&L&M4N__jkRf63DKloXV=Yq&H2Rke2cGF z3pzwxS*sDt+@(+%`i;CRPR@d_(v&&a#da9%vGOI~0lLHjfG2Sn8vA2fi y!{bdNkZvETV=WN!tXP00a*D+CQ|gP38*H1|9>x$`;p#s>psJ#lLWP`p$o~KWqg`S_vv52zmi002TIMOn??JLva(b|2^Wy0PRg4*(D- z+R4bME6K<(sJpqmv~z?30E!XGdbs*py%cC8O(omF`-*st5sZqdWYSR#3_9hciIUP0 z{7+Fcq#CWCqwdd)=#a`yWA+$Uq{>yChhrxvdsLXqtgAlQ+CKkw{q3@;{=C^{=<-GH zLOK-yUhJ)DM^ub2S<3u^;xXL-b$VhSBNXF)OMr0sy(>tQabIjq45s?k!CjJ60r7bS)So3P{4X(`?8GtCuXOuayE{)-38=z99evvD)pkujV|z3k;YfJL zlMp{Yd{?8M6kjq#mAeu3Cg8oW71g|u*B3CGgxJu^gqFiv$K zKD5(r7gm3K>r)ZR$S-0T%=J?ikCYmn>4)Zg&4fx1A@j79h*K9AE^ej>Pkfm_zGOb6CVtRrMuHdU z*8tfDUtFy!BcsXc2sN~9$mooca1~pd*L+uG1n(H*MsQ8q!D?9Y@M1d z+X9-IH}RJ`F@7}89-nkt!N$pfL)RX|M_jt-YZ?EZ7y;LZ%RzAg2{QdeKTQg;59uy* zS!zh;!!uiBtv1VL^qI^p6e?JE89ntQaCJu?PI7L?Q55#E(Hx^*M|O{QXnShz8*a}1 zxH5pIvT>{X(_`3F!r!T6aP(PKd`~s&S$TdT6JEYxyl9M}ej8ULq2-cRe1{w2eVbmo zB@VddKq8UhO+Rv$eZSm+028Gy;A=2oO93D%mQ@zN{?ViESQ?<6jkUyXWlmHQh*i=} zh`^K}xhLJqPJ%@y`5^6n19#Al0Zu^>l{qgv2F#pFpOCW^r<}?Wx1q&!at)R zfH!z&nb#QlWEp!4=Rgt|#K0U9%SU3>fmtD!K`PQggC{ASz|KshBsCVVA{)dWPt^m- zBQOZmW=xMaToYMiaH9ouXQenAW(~Y}QO8c{@{9 zlq25XXCG%*<}hL(Oj1rFdJfcyvwv|~$f{mdLGjR#FgTBA!t;z`bZGl3D1dUk8)3Vk1$iMHWznP>xcIV%ZcF?-WApru2a~V zx>IS5q;HL9vS;wwqrFrx`4gijHAAwQ(wT0VNN_6r3!LMN=NDQN^gj0@=VI^|5f9%J zN}u*q%M-U#ik-a?vBGoXtUQ-O`eNV+aB8XKwe%f7mX*GMD1o>YofZBnd2V}vt+`8! zP|q`Vff?9{{fJYMi)b5PZ+T03-(k6h*h8y1{`vvh4b2VH4Z@8=sh7bs!6CsEgvIo5 z*obd#tGtxFbgpLZqWpA>I8{}&OiWcwDvb#Bl1Qs+hDukOijaYeTVI|-d8>JI>rHEZ z@HtVFRpdMH+pf22B8!ebqt)F53)~AT_BB(xAqJ_SaYzrO-!J)+^rsqrm|Q^UjAe4C zMwEm>7`HH2xK1m$ce_ULb9A}3zH_DH=iSehwa=?LE9aa%mfqR#Ib~Wj_I>I6GT+tq zvU-pp9h@#!LvG|^l(0uVFHm!^x4W0PM=>Kb2dx#U+?;znH$A)Lo-K9{tm0baTDPGH zKk*#!G~Pta;&~juA_M7wOx)x%p_!dSI~ns~Bw-f>2?QUg+{QyU+B|!`KDc{}CV>R) zZAVAC-UGvD36!7I_|3evFf)M~yBpWmeS1VO!Gy}*>fuPyId z6r`r4g0eqJ4bQ~xa-XT4^_x$d8yp5MpVOKRsSH(+a5F>l1oMQnB?S4apPfjh>FB@I zH_`X1Q@A)ev?2{b^`O>CMe1J~i`S;iL;D;i1~k~1>=KR=k`v-`GIFdn26IP8bLGou zk-#}&L$XCmEXz86F01|Sxo)+HUq}L1mEE*r{uirZ-GeBxhr_5W@@A%66X{oNV<8O@ zL=ll4Da@I9M@pZS4&KNl>M_^GJrVZYn8D{@`t15S)XN# z{0d+1eirP)rlbdf{*hJxtV)ZVo%69r1Zd^?(Z>>038BG3l~rXe?0lVhb9abkvtXSr zX-m11g^ex!1#j8{t4B(T;(XzSngKN5h=OCDQ(^7lnyNR>t9E~l@7ZZ(h&1|mv*bGq z`>_cmwhwk{L~hjn@EP zRuz)h!})AMBGNcYm%K4E6;f6|Q-V-CTD|=KbLV-rvNemy;|rddauPFk)0rO8b`16LkP5oq?gGi;c&c9@+4&NI)?)pk2c z80_d6HMGOK$H3KU8q@XeH$(jm(w;(-4HGVNg9|1#xVsv=mp^N(mz;NF7UnC5ea(LP z&;OdlrNn(s6CY+rxEPbubykp6P!pU>R3msTM1O(YI+!OipeqJDA`m}Fw-Z*FkP7&5 zXS8qVcED)w8`u84lm@mgbe*T$K<|`RLg5gaNDR3`a6K?ub!$VM`4j4O`1Sm<3m^TM zn%Bn|av0uCk821uqT%&6vH!B`USIEIJ)gi8s26KSSnqR1eLfeuGdex*%>1p+!~JIP z%qYlc*kyCU--GQ=?O+jfe*gUW!Ol0}YxAq@4YSz0xyAii{|k$r_NcfO`bFfx>zkE` zo8HaXmBN$4^H5+REbq%4%DY(hmU9{jcu$)R043csb(f#UvLm^pO0m`Vas?H$e;s#?7;uYlOV-$bDz`y`;vwjKIl$HM%{r3&ZXbXqG0t10w zUS7Oj0=zD6Hb8z52n6JN27LC6=Qo1K-P;*%f#7j=XZqX7|Jsp-xm&r}y@K1hI5YgQ zYhmf)0f#a&{&Dp0@pqgsgx!BUIlKQWt=|a(|7d{xynMj_iw3uQ`Tx-VX#S@CmDk_y zAb*U3)$I^4M*~?qCz!MQ@6g1BL?M59`7gzP;`|3u|35@w;eQhUq4)>!PaNPEZg#NW zCHhkcaefH!zhwWyLx6v(^pC3j-IBkgzk4G700R7Xf5jghOux?r0C4k_WTmuivDXb9 z9JS@hZ#{jlXFOAzw(zeALMi5|v2(~eD3Wy56XGQ&>4PF9P^~S%9Qm71UGytv59uSy zqzUjy@fk^_qhvWW*|qQG5u4^GQ`pwVA*;~>^9CEd^WFQ6PDN_t4emA@8K5PQ%@AZ? zU!FZMvFbI+o``d9ZWT>%FfU5F6w&b}bj`{@hzFBH>8PhyMMiUl`>9Z>dt<27*}`7u z+k*Z>M0i4)xdJokK#6sr7lQKKH?vJrF4VgRoxUBOU4c!NEz}mdf(=r9p%gUPcVT0? zT|XVwuUEEu(@7yKXRr7|74!N-vPlw8ow+H+Mji`(K)ZJP-EQyuTV=y!)4`87tenJM z%K53@y=?s70_E`CNFAc&=TGNf)i0FCHww}P@8&p4v94IJzvI*5>obQ9_~#r~Y-7o- zdUAvMUE->qI;e5J1AcB@KV#tJB-15&2Emz?qsr|Bw6qKr{xs1+@vuG!mLZ4akNVZn zJW_B1Ws<46nh6MYgcSV#za_pO6(9SgV?1uJL`7IABevZ$uHB)vcnQZ5dNf^acxNDyL1l|=aB^|v^PZq; zQMVIzm1b?h(lY5F(n4w__uMTJP_S)jjkt%6AElwuD!HSATU?blS8;TMB1z%V*EnV5 zIf3>lD$BWKX(fHUF>w}gf-~_qm!kqwt^?g@1WNu!e{~@cZ*HQd;y6l6O=r3ni@INl zS9nA%2#lxsB-47vY-M!QnAQ~w2rWlxAikq%=ZaMUjUEemx&jtFCck)SK`N8Y?{-9~M`b zmRLl^Mv@tO4|t9z^zScbF@VAE&VrZ@eHs;2mGXaOLqpJP(-Y*%eWi?eYhOHoJ$iQs zfpdm}XlHqUDI&QUQr9hbVeS(#Psj6G4FL#i{>sGhtDgmBChLMvu`Mkc>43IT`}0li zowi#$J3GOP&X0AI_AX0$RRRX4wUwXAcy_ihhivFbN+vo5;}itcyl*OQRNcXZYD>jb z>siHc?1QJi3LDhYM4_eBQWUbKwUw#e^f(qmf=23SfiZH!Hfwe&cKmpX%c5p)mSavvtn;MAa)>w`(*RTryOx)sjX8g@95~LFNrPS69QAhJKh*Hnz=mV6%@`$x`8*F zczvnxyL8*VyBeaVXYD(3~CIVbJ>@HpQwT?HnOdV`F4i3_4-& zH%y!#Cz7pbXx3=g<#(?hRhf(YTG>HbN7$%0+A*c@8Zh2l$0^CHs}rTYy}aLavrPkO zas**`jh|CSsfUDb=xo4ZMvDA;h6R$M?E<^)E5=0LSSa)%_gGCx@cwrHo=C_uR`W;IhRIAN9I`{K6b?JPmEs| z^|*;4pwL(01gP_9hvH)OCd!dgqT!bU+Rc}!lY~)v!gGj^3=p;{RW(A*LOw=3dFu7J{I(wT$bicJJj9 z&y=%qKv|rico-y!04IROq!!9ng$+GlaypMrRw=(WdnhOmB*DRYSQ0IkUgTHe^R(zV zes2xC?Kbc!`G!ptmyKnoY#eDRWE?KH+x74v?OpxH?3E@iuFhGBfU}*No1DlQ9Elq%9il+1a#A%qg25O-d&&1{|nf^S|l;qT8OQp?&{s+P(w^slF diff --git a/docs/en_US/storage_manager.rst b/docs/en_US/storage_manager.rst index 36bb5d6f8..aee923598 100644 --- a/docs/en_US/storage_manager.rst +++ b/docs/en_US/storage_manager.rst @@ -20,47 +20,53 @@ Use icons on the top of the *Storage Manager* window to manage storage: Use the ``Home`` icon |home| to return to the home directory. -.. |home| image:: images/home.png +.. |home| image:: images/sm_home.png Use the ``Up Arrow`` icon |uparrow| to return to the previous directory. -.. |uparrow| image:: images/uparrow.png +.. |uparrow| image:: images/sm_go_back.png Use the ``Refresh`` icon |refresh| to display the most-recent files available. -.. |refresh| image:: images/refresh.png +.. |refresh| image:: images/sm_refresh.png Select the ``Download`` icon |download| to download the selected file. -.. |download| image:: images/download.png - -Select the ``Delete`` icon |delete| to delete the selected file or folder. - -.. |delete| image:: images/delete.png - -Select the ``Edit`` icon |edit| to rename a file or folder. - -.. |edit| image:: images/edit.png - -Use the ``Upload`` icon |upload| to upload a file. - -.. |upload| image:: images/upload.png +.. |download| image:: images/sm_download.png Use the ``New Folder`` icon |folder| to add a new folder. -.. |folder| image:: images/folder.png - -Use the ``Grid View`` icon |gridview| to display all the files and folders in a grid view. +.. |folder| image:: images/sm_new_folder.png -.. |gridview| image:: images/gridview.png +Use the *Format* drop down list to select the format of the files to be displayed; choose from *sql*, *csv*, or *All Files*. -Use the ``Table View`` icon |tableview| to display all the files and folders in a list view. +Other Options +********************* -.. |tableview| image:: images/tableview.png +.. image:: images/sm_options.png + :alt: Other options + :align: center -Click on the check box next to *Show hidden files and folders* at the bottom of the window to view hidden files and folders. +.. table:: + :class: longtable + :widths: 1 5 + + +----------------------+---------------------------------------------------------------------------------------------------+ + | Menu | Behavior | + +======================+===================================================================================================+ + | *Rename* | Click the *Rename* option to rename a file/folder. | + +----------------------+---------------------------------------------------------------------------------------------------+ + | *Delete* | Click the *Delete* option to rename a file/folder. | + +----------------------+---------------------------------------------------------------------------------------------------+ + | *Upload* | Click the *Upload* option to upload multiple files to the current folder. | + +----------------------+---------------------------------------------------------------------------------------------------+ + | *List View* | Click the *List View* option to to display all the files and folders in a list view. | + +----------------------+---------------------------------------------------------------------------------------------------+ + | *Grid View* | Click the *Grid View* option to to display all the files and folders in a grid view. | + +----------------------+---------------------------------------------------------------------------------------------------+ + | *Show Hidden Files* | Click the *Show Hidden Files* option to view hidden files and folders. | + +----------------------+---------------------------------------------------------------------------------------------------+ -Use the *Format* drop down list to select the format of the files to be displayed; choose from *sql*, *csv*, or *All Files*. You can also download backup files through *Storage Manager* at the successful completion of the backups taken through :ref:`Backup Dialog `, :ref:`Backup Global Dialog `, or :ref:`Backup Server Dialog `. diff --git a/runtime/package.json b/runtime/package.json index 1051ba603..0015fbc95 100644 --- a/runtime/package.json +++ b/runtime/package.json @@ -7,6 +7,7 @@ "license": "PostgreSQL", "chromium-args": "--disable-popup-blocking --disable-gpu", "user-agent": "Nwjs:%nwver-%osinfo-%chromium_ver", + "nodejs": true, "window": { "width": 750, "height": 600, diff --git a/web/package.json b/web/package.json index 7e4b2cc36..c99217714 100644 --- a/web/package.json +++ b/web/package.json @@ -111,12 +111,12 @@ "closest": "^0.0.1", "codemirror": "^5.59.2", "context-menu": "^2.0.0", + "convert-units": "^2.3.4", "css-loader": "^5.0.1", "cssnano": "^5.0.2", "dagre": "^0.8.4", "date-fns": "^2.24.0", "diff-arrays-of-objects": "^1.1.8", - "dropzone": "^5.9.3", "html2canvas": "^1.0.0-rc.7", "immutability-helper": "^3.0.0", "imports-loader": "^2.0.0", @@ -150,6 +150,7 @@ "react-data-grid": "git+https://github.com/adityatoshniwal/react-data-grid.git/#8d9bc16ddd7c419acfbbd1c1cc2b70eb9f5b453c", "react-dom": "^17.0.1", "react-draggable": "^4.4.4", + "react-dropzone": "^14.2.1", "react-leaflet": "^3.2.2", "react-rnd": "^10.3.5", "react-router-dom": "^6.2.2", @@ -165,7 +166,6 @@ "socket.io-client": "^4.0.0", "split.js": "^1.5.10", "styled-components": "^5.2.1", - "tablesorter": "^2.31.2", "tempusdominus-bootstrap-4": "^5.1.2", "tempusdominus-core": "^5.19.3", "underscore": "^1.13.1", diff --git a/web/pgadmin/browser/static/js/node.js b/web/pgadmin/browser/static/js/node.js index 2d12c4ed9..199ee986f 100644 --- a/web/pgadmin/browser/static/js/node.js +++ b/web/pgadmin/browser/static/js/node.js @@ -551,7 +551,25 @@ define('pgadmin.browser.node', [ } }, + registerDockerPanel: function(docker, name, params) { + var w = docker || pgBrowser.docker, + p = w.findPanels(name); + + if (p && p.length == 1) + return; + p = new pgBrowser.Panel({ + name: name, + showTitle: true, + isCloseable: true, + isPrivate: true, + isLayoutMember: false, + canMaximise: true, + content: '

', + ...params, + }); + p.load(w); + }, registerUtilityPanel: function(docker) { var w = docker || pgBrowser.docker, p = w.findPanels('utility_props'); diff --git a/web/pgadmin/misc/bgprocess/static/js/bgprocess.js b/web/pgadmin/misc/bgprocess/static/js/bgprocess.js index b007fec3f..ddc965e7a 100644 --- a/web/pgadmin/misc/bgprocess/static/js/bgprocess.js +++ b/web/pgadmin/misc/bgprocess/static/js/bgprocess.js @@ -9,7 +9,7 @@ define('misc.bgprocess', [ 'sources/pgadmin', 'sources/gettext', 'sources/url_for', 'underscore', - 'jquery', 'pgadmin.browser', 'alertify', + 'jquery', 'pgadmin.browser', 'alertify', 'pgadmin.tools.file_manager', ], function( pgAdmin, gettext, url_for, _, $, pgBrowser, Alertify ) { @@ -625,9 +625,7 @@ define('misc.bgprocess', [ var self = this; if(self.current_storage_dir) { - pgBrowser.Events.trigger( - 'pgadmin:tools:storage_manager', self.current_storage_dir - ); + pgAdmin.Tools.FileManager.openStorageManager(self.current_storage_dir); } }, }); diff --git a/web/pgadmin/misc/file_manager/__init__.py b/web/pgadmin/misc/file_manager/__init__.py index f9562b1a8..bef74fb71 100644 --- a/web/pgadmin/misc/file_manager/__init__.py +++ b/web/pgadmin/misc/file_manager/__init__.py @@ -28,9 +28,11 @@ from flask_babel import gettext from flask_security import login_required from pgadmin.utils import PgAdminModule from pgadmin.utils import get_storage_directory -from pgadmin.utils.ajax import make_json_response +from pgadmin.utils.ajax import make_json_response, unauthorized, \ + internal_server_error from pgadmin.utils.preferences import Preferences from pgadmin.utils.constants import PREF_LABEL_OPTIONS, MIMETYPE_APP_JS +from pgadmin.settings.utils import get_file_type_setting # Checks if platform is Windows if _platform == "win32": @@ -132,9 +134,9 @@ class FileManagerModule(PgAdminModule): list: a list of url endpoints exposed to the client. """ return [ + 'file_manager.init', 'file_manager.filemanager', 'file_manager.index', - 'file_manager.get_trans_id', 'file_manager.delete_trans_id', 'file_manager.save_last_dir', 'file_manager.save_file_dialog_view', @@ -196,74 +198,62 @@ def utility(): mimetype=MIMETYPE_APP_JS) -@blueprint.route("/file_manager.js") -@login_required -def file_manager_js(): - """render the required javascript""" - return Response(response=render_template( - "file_manager/js/file_manager.js", _=gettext), - status=200, - mimetype=MIMETYPE_APP_JS) - - -@blueprint.route("/en.json") -@login_required -def language(): - """render the required javascript""" - return Response(response=render_template( - "file_manager/js/languages/en.json", _=gettext), - status=200) - - -@blueprint.route("/file_manager_config.js") -@login_required -def file_manager_config_js(): - """render the required javascript""" - return Response(response=render_template( - "file_manager/js/file_manager_config.js", _=gettext), - status=200, - mimetype=MIMETYPE_APP_JS) - - -@blueprint.route("//file_manager_config.json") -@login_required -def file_manager_config(trans_id): - """render the required json""" - data = Filemanager.get_trasaction_selection(trans_id) - pref = Preferences.module('file_manager') - file_dialog_view = pref.preference('file_dialog_view').get()[0] - show_hidden_files = pref.preference('show_hidden_files').get() - - return Response(response=render_template( - "file_manager/js/file_manager_config.json", - _=gettext, - data=data, - file_dialog_view=file_dialog_view, - show_hidden_files=show_hidden_files - ), - status=200, - mimetype="application/json" - ) - - @blueprint.route( - "/get_trans_id", methods=["GET", "POST"], endpoint='get_trans_id' + "/init", methods=["POST"], endpoint='init' ) @login_required -def get_trans_id(): +def init_filemanager(): if len(req.data) != 0: configs = json.loads(req.data) trans_id = Filemanager.create_new_transaction(configs) - global transid - transid = trans_id - return make_json_response( - data={'fileTransId': transid, 'status': True} - ) + data = Filemanager.get_trasaction_selection(trans_id) + pref = Preferences.module('file_manager') + file_dialog_view = pref.preference('file_dialog_view').get() + if type(file_dialog_view) == list: + file_dialog_view = file_dialog_view[0] + + last_selected_format = get_file_type_setting(data['supported_types']) + # in some cases, the setting may not match with available types + if last_selected_format not in data['supported_types']: + last_selected_format = data['supported_types'][0] + + res_data = { + 'transId': trans_id, + "options": { + "culture": "en", + "lang": "py", + "defaultViewMode": file_dialog_view, + "autoload": True, + "showFullPath": False, + "dialog_type": data['dialog_type'], + "show_hidden_files": + pref.preference('show_hidden_files').get(), + "fileRoot": data['fileroot'], + "capabilities": data['capabilities'], + "allowed_file_types": data['supported_types'], + "platform_type": data['platform_type'], + "show_volumes": data['show_volumes'], + "homedir": data['homedir'], + "last_selected_format": last_selected_format + }, + "security": { + "uploadPolicy": data['security']['uploadPolicy'], + "uploadRestrictions": data['security']['uploadRestrictions'], + }, + "upload": { + "multiple": data['upload']['multiple'], + "number": 20, + "fileSizeLimit": data['upload']['fileSizeLimit'], + "imagesOnly": False + } + } + + return make_json_response(data=res_data) @blueprint.route( - "/del_trans_id/", - methods=["GET", "POST"], endpoint='delete_trans_id' + "/delete_trans_id/", + methods=["DELETE"], endpoint='delete_trans_id' ) @login_required def delete_trans_id(trans_id): @@ -279,9 +269,7 @@ def delete_trans_id(trans_id): @login_required def save_last_directory_visited(trans_id): blueprint.last_directory_visited.set(req.json['path']) - return make_json_response( - data={'status': True} - ) + return make_json_response(status=200) @blueprint.route( @@ -291,9 +279,7 @@ def save_last_directory_visited(trans_id): @login_required def save_file_dialog_view(trans_id): blueprint.file_dialog_view.set(req.json['view']) - return make_json_response( - data={'status': True} - ) + return make_json_response(status=200) @blueprint.route( @@ -303,9 +289,7 @@ def save_file_dialog_view(trans_id): @login_required def save_show_hidden_file_option(trans_id): blueprint.show_hidden_files.set(req.json['show_hidden']) - return make_json_response( - data={'status': True} - ) + return make_json_response(status=200) class Filemanager(object): @@ -321,14 +305,6 @@ class Filemanager(object): def __init__(self, trans_id): self.trans_id = trans_id - self.patherror = encode_json( - { - 'Error': gettext( - 'No permission to operate on specified path.' - ), - 'Code': 0 - } - ) self.dir = get_storage_directory() if self.dir is not None and isinstance(self.dir, list): @@ -387,7 +363,7 @@ class Filemanager(object): # tuples with (capabilities, files_only, folders_only, title) capability_map = { 'select_file': ( - ['select_file', 'rename', 'upload', 'create'], + ['select_file', 'rename', 'upload', 'delete'], True, False, gettext("Select File") @@ -421,6 +397,8 @@ class Filemanager(object): # get last visited directory, if not present then traverse in reverse # order to find closest parent directory + if 'init_path' in params: + blueprint.last_directory_visited.get(params['init_path']) last_dir = blueprint.last_directory_visited.get() check_dir_exists = False if last_dir is None: @@ -436,9 +414,8 @@ class Filemanager(object): # create configs using above configs configs = { - # for JS json compatibility - "fileroot": last_dir.replace('\\', '\\\\'), - "homedir": homedir.replace('\\', '\\\\'), + "fileroot": last_dir, + "homedir": homedir, "dialog_type": fm_type, "title": title, "upload": { @@ -499,14 +476,14 @@ class Filemanager(object): file_manager_data = session['fileManagerData'] # Return from the function if transaction id not found if str(trans_id) not in file_manager_data: - return make_json_response(data={'status': True}) + return make_json_response(status=200) # Remove the information of unique transaction id # from the session variable. file_manager_data.pop(str(trans_id), None) session['fileManagerData'] = file_manager_data - return make_json_response(data={'status': True}) + return make_json_response(status=200) @staticmethod def _get_drives_with_size(drive_name=None): @@ -590,7 +567,7 @@ class Filemanager(object): :param orig_path: path after user dir :return: """ - files = {} + files = [] for f in sorted(os.listdir(orig_path)): system_path = os.path.join(os.path.join(orig_path, f)) @@ -617,14 +594,13 @@ class Filemanager(object): if files_only == 'true': continue file_extension = "dir" - user_path = "{0}/".format(user_path) # filter files based on file_type elif Filemanager._skip_file_extension( file_type, supported_types, folders_only, file_extension): continue # create a list of files and folders - files[f] = { + files.append({ "Filename": f, "Path": user_path, "file_type": file_extension, @@ -634,7 +610,7 @@ class Filemanager(object): "Date Modified": modified, "Size": sizeof_fmt(getsize(system_path)) } - } + }) return files @@ -649,23 +625,16 @@ class Filemanager(object): path = unquote(path) - try: - Filemanager.check_access_permission(in_dir, path) - except Exception as e: - Filemanager.resume_windows_warning() - files = { - 'Code': 0, - 'Error': str(e) - } - return files + Filemanager.check_access_permission(in_dir, path) + Filemanager.resume_windows_warning() - files = {} + files = [] if (_platform == "win32" and (path == '/' or path == '\\'))\ and in_dir is None: drives = Filemanager._get_drives_with_size() for drive, drive_size in drives: path = file_name = "{0}:".format(drive) - files[file_name] = { + files.append({ "Filename": file_name, "Path": path, "file_type": 'drive', @@ -675,7 +644,7 @@ class Filemanager(object): "Date Modified": "", "Size": drive_size } - } + }) Filemanager.resume_windows_warning() return files @@ -683,10 +652,9 @@ class Filemanager(object): if not path_exists(orig_path): Filemanager.resume_windows_warning() - return { - 'Code': 0, - 'Error': gettext("'{0}' file does not exist.").format(path) - } + return make_json_response( + status=404, + errormsg=gettext("'{0}' file does not exist.").format(path)) user_dir = path folders_only = trans_data.get('folders_only', '') @@ -705,11 +673,7 @@ class Filemanager(object): if (hasattr(e, 'strerror') and e.strerror == gettext('Permission denied')): err_msg = str(e.strerror) - - files = { - 'Code': 0, - 'Error': err_msg - } + return unauthorized(err_msg) Filemanager.resume_windows_warning() return files @@ -735,9 +699,10 @@ class Filemanager(object): # Do not allow user to access outside his storage dir # in server mode. - if not orig_path.startswith(in_dir): - raise InternalServerError( - gettext("Access denied ({0})").format(path)) + try: + pathlib.Path(orig_path).relative_to(in_dir) + except ValueError: + raise PermissionError(gettext("Access denied ({0})").format(path)) @staticmethod def get_abs_path(in_dir, path): @@ -789,33 +754,13 @@ class Filemanager(object): self.dir = "" orig_path = "{0}{1}".format(self.dir, path) - try: - Filemanager.check_access_permission(self.dir, path) - except Exception as e: - thefile = { - 'Filename': split_path(path)[-1], - 'FileType': '', - 'Path': path, - 'Error': str(e), - 'Code': 0, - 'Info': '', - 'Properties': { - date_created: '', - date_modified: '', - 'Width': '', - 'Height': '', - 'Size': '' - } - } - return thefile + Filemanager.check_access_permission(self.dir, path) user_dir = path thefile = { 'Filename': split_path(orig_path)[-1], 'FileType': '', 'Path': user_dir, - 'Error': '', - 'Code': 1, 'Info': '', 'Properties': { date_created: '', @@ -827,10 +772,9 @@ class Filemanager(object): } if not path_exists(orig_path): - thefile['Error'] = gettext( - "'{0}' file does not exist.").format(path) - thefile['Code'] = -1 - return thefile + return make_json_response( + status=404, + errormsg=gettext("'{0}' file does not exist.").format(path)) if split_path(user_dir)[-1] == '/'\ or os.path.isfile(orig_path) is False: @@ -868,19 +812,12 @@ class Filemanager(object): Rename file or folder """ if not self.validate_request('rename'): - return self.ERROR_NOT_ALLOWED + return unauthorized(self.ERROR_NOT_ALLOWED['Error']) the_dir = self.dir if self.dir is not None else '' - try: - Filemanager.check_access_permission(the_dir, old) - Filemanager.check_access_permission(the_dir, new) - except Exception as e: - res = { - 'Error': str(e), - 'Code': 0 - } - return res + Filemanager.check_access_permission(the_dir, old) + Filemanager.check_access_permission(the_dir, new) # check if it's dir if old[-1] == '/': @@ -906,39 +843,27 @@ class Filemanager(object): try: os.rename(oldpath_sys, newpath_sys) except Exception as e: - code = 0 - error_msg = "{0} {1}".format( - gettext('There was an error renaming the file:'), e) + return internal_server_error("{0} {1}".format( + gettext('There was an error renaming the file:'), e)) - result = { + return { 'Old Path': old, 'Old Name': oldname, 'New Path': newpath, 'New Name': newname, - 'Error': error_msg, - 'Code': code } - return result - def delete(self, path=None, req=None): """ Delete file or folder """ if not self.validate_request('delete'): - return self.ERROR_NOT_ALLOWED + return unauthorized(self.ERROR_NOT_ALLOWED['Error']) the_dir = self.dir if self.dir is not None else '' orig_path = "{0}{1}".format(the_dir, path) - try: - Filemanager.check_access_permission(the_dir, path) - except Exception as e: - res = { - 'Error': str(e), - 'Code': 0 - } - return res + Filemanager.check_access_permission(the_dir, path) err_msg = '' code = 1 @@ -948,23 +873,17 @@ class Filemanager(object): else: os.remove(orig_path) except Exception as e: - code = 0 - err_msg = str(e.strerror) + return internal_server_error("{0} {1}".format( + gettext('There was an error deleting the file:'), e)) - result = { - 'Path': path, - 'Error': err_msg, - 'Code': code - } - - return result + return make_json_response(status=200) def add(self, req=None): """ File upload functionality """ if not self.validate_request('upload'): - return self.ERROR_NOT_ALLOWED + return unauthorized(self.ERROR_NOT_ALLOWED['Error']) the_dir = self.dir if self.dir is not None else '' err_msg = '' @@ -986,7 +905,7 @@ class Filemanager(object): ) ).relative_to(the_dir) except ValueError: - return self.ERROR_NOT_ALLOWED + return unauthorized(self.ERROR_NOT_ALLOWED['Error']) with open(new_name, 'wb') as f: while True: @@ -996,25 +915,15 @@ class Filemanager(object): break f.write(data) except Exception as e: - code = 0 - err_msg = str(e.strerror) if hasattr(e, 'strerror') else str(e) + return internal_server_error("{0} {1}".format( + gettext('There was an error adding the file:'), e)) - try: - Filemanager.check_access_permission(the_dir, path) - except Exception as e: - res = { - 'Error': str(e), - 'Code': 0 - } - return res + Filemanager.check_access_permission(the_dir, path) - result = { + return { 'Path': path, 'Name': new_name, - 'Error': err_msg, - 'Code': code } - return result def is_file_exist(self, path, name, req=None): """ @@ -1026,48 +935,40 @@ class Filemanager(object): name = unquote(name) path = unquote(path) - try: - orig_path = "{0}{1}".format(the_dir, path) - Filemanager.check_access_permission( - the_dir, "{}{}".format(path, name)) - new_name = "{0}{1}".format(orig_path, name) - if not os.path.exists(new_name): - code = 0 - except Exception as e: + orig_path = "{0}{1}".format(the_dir, path) + Filemanager.check_access_permission( + the_dir, "{}{}".format(path, name)) + + new_name = "{0}{1}".format(orig_path, name) + if not os.path.exists(new_name): code = 0 - if hasattr(e, 'strerror'): - err_msg = str(e.strerror) - else: - err_msg = str(e) - result = { + return { 'Path': path, 'Name': name, - 'Error': err_msg, - 'Code': code + 'Code': code, } - return result - @staticmethod - def get_new_name(in_dir, path, new_name, count=1): + def get_new_name(in_dir, path, name): """ Utility to provide new name for folder if file with same name already exists """ - last_char = new_name[-1] - t_new_path = "{}/{}{}_{}".format(in_dir, path, new_name, count) - if last_char == 'r' and not path_exists(t_new_path): - return t_new_path, new_name - else: - last_char = int(t_new_path[-1]) + 1 - new_path = "{}/{}{}_{}".format(in_dir, path, new_name, last_char) - if path_exists(new_path): - count += 1 - return Filemanager.get_new_name(in_dir, path, new_name, count) + new_name = name + count = 0 + while True: + file_path = "{}{}/".format(path, new_name) + create_path = file_path + if in_dir != "": + create_path = "{}/{}".format(in_dir, file_path) + + if not path_exists(create_path): + return create_path, file_path, new_name else: - return new_path, new_name + count += 1 + new_name = "{}_{}".format(name, count) @staticmethod def check_file_for_bom_and_binary(filename, enc="utf-8"): @@ -1125,17 +1026,15 @@ class Filemanager(object): append({os.path.basename(filename): enc}) except IOError as ex: - status = False # we don't want to expose real path of file # so only show error message. if ex.strerror == 'Permission denied': - err_msg = str(ex.strerror) + return unauthorized(str(ex.strerror)) else: - err_msg = str(ex) + return internal_server_error(str(ex)) except Exception as ex: - status = False - err_msg = str(ex) + return internal_server_error(str(ex)) # Remove root storage path from error message # when running in Server mode @@ -1146,52 +1045,30 @@ class Filemanager(object): return status, err_msg, is_binary, is_startswith_bom, enc - def addfolder(self, path, name): + def addfolder(self, path, name, req=None): """ Functionality to create new folder """ if not self.validate_request('create'): - return self.ERROR_NOT_ALLOWED + return unauthorized(self.ERROR_NOT_ALLOWED['Error']) - the_dir = self.dir if self.dir is not None else '' + user_dir = self.dir if self.dir is not None else '' + + Filemanager.check_access_permission(user_dir, "{}{}".format( + path, name)) + create_path, new_path, new_name = \ + self.get_new_name(user_dir, path, name) try: - Filemanager.check_access_permission(the_dir, "{}{}".format( - path, name)) + os.mkdir(create_path) except Exception as e: - res = { - 'Error': str(e), - 'Code': 0 - } - return res - - if the_dir != "": - new_path = "{}/{}{}/".format(the_dir, path, name) - else: - new_path = "{}{}/".format(path, name) - - err_msg = '' - code = 1 - new_name = name - if not path_exists(new_path): - try: - os.mkdir(new_path) - except Exception as e: - code = 0 - err_msg = str(e.strerror) - else: - new_path, new_name = self.get_new_name(the_dir, path, name) - try: - os.mkdir(new_path) - except Exception as e: - code = 0 - err_msg = str(e.strerror) + return internal_server_error(str(e)) result = { 'Parent': path, + 'Path': new_path, 'Name': new_name, - 'Error': err_msg, - 'Code': code + 'Date Modified': time.ctime(time.time()) } return result @@ -1201,20 +1078,14 @@ class Filemanager(object): Functionality to download file """ if not self.validate_request('download'): - return self.ERROR_NOT_ALLOWED + return unauthorized(self.ERROR_NOT_ALLOWED['Error']) the_dir = self.dir if self.dir is not None else '' orig_path = "{0}{1}".format(the_dir, path) - try: - Filemanager.check_access_permission( - the_dir, "{}{}".format(path, path) - ) - except Exception as e: - resp = Response(str(e)) - resp.headers['Content-Disposition'] = \ - 'attachment; filename=' + name - return resp + Filemanager.check_access_permission( + the_dir, "{}{}".format(path, path) + ) name = os.path.basename(path) if orig_path and len(orig_path) > 0: @@ -1232,12 +1103,7 @@ class Filemanager(object): def permission(self, path=None, req=None): the_dir = self.dir if self.dir is not None else '' res = {'Code': 1} - try: - Filemanager.check_access_permission(the_dir, path) - except Exception as e: - err_msg = str(e) - res['Code'] = 0 - res['Error'] = err_msg + Filemanager.check_access_permission(the_dir, path) return res @@ -1272,9 +1138,12 @@ def file_manager(trans_id): } mode = req.args['mode'] + func = getattr(my_fm, mode) try: - func = getattr(my_fm, mode) res = func(**kwargs) - return make_json_response(data={'result': res, 'status': True}) - except Exception: - return getattr(my_fm, mode)(**kwargs) + except PermissionError as e: + return unauthorized(str(e)) + + if type(res) == Response: + return res + return make_json_response(data={'result': res, 'status': True}) diff --git a/web/pgadmin/misc/file_manager/static/js/FileManagerModule.jsx b/web/pgadmin/misc/file_manager/static/js/FileManagerModule.jsx new file mode 100644 index 000000000..2c8bd8aa6 --- /dev/null +++ b/web/pgadmin/misc/file_manager/static/js/FileManagerModule.jsx @@ -0,0 +1,121 @@ + +///////////////////////////////////////////////////////////// +// +// pgAdmin 4 - PostgreSQL Tools +// +// Copyright (C) 2013 - 2022, The pgAdmin Development Team +// This software is released under the PostgreSQL Licence +// +////////////////////////////////////////////////////////////// +import gettext from 'sources/gettext'; +import Notifier from '../../../../static/js/helpers/Notifier'; +import React from 'react'; +import FileManager from './components/FileManager'; +import { getBrowser } from '../../../../static/js/utils'; + +export default class FileManagerModule { + static instance; + + static getInstance(...args) { + if(!FileManagerModule.instance) { + FileManagerModule.instance = new FileManagerModule(...args); + } + return FileManagerModule.instance; + } + + constructor(pgAdmin) { + this.pgAdmin = pgAdmin; + } + + init() { + if(this.initialized) + return; + this.initialized = true; + + if(this.pgAdmin.server_mode == 'True') { + // Define the nodes on which the menus to be appear + this.pgAdmin.Browser.add_menus([{ + name: 'storage_manager', + module: this, + applies: ['tools'], + callback: 'openStorageManager', + priority: 11, + label: gettext('Storage Manager...'), + enable: true, + }]); + } + } + + openStorageManager(path) { + this.show({ + dialog_type: 'storage_dialog', + supported_types: ['sql', 'csv', 'json', '*'], + dialog_title: gettext('Storage Manager'), + path: path, + }); + } + + showInternal(params, onOK, onCancel, modalObj) { + const modal = modalObj || Notifier; + let title = params.dialog_title; + if(!title) { + if(params.dialog_type == 'create_file') { + title = gettext('Save File'); + } else if(params.dialog_type == 'select_file') { + title = gettext('Select File'); + } else { + title = gettext('Storage Manager'); + } + } + modal.showModal(title, (closeModal)=>{ + return ( + + ); + }, { + isResizeable: true, + onClose: onCancel, + dialogWidth: 700, dialogHeight: 400 + }); + } + + showNative(params, onOK, onCancel) { + // https://docs.nwjs.io/en/latest/References/Changes%20to%20DOM/ + let fileEle = document.createElement('input'); + let accept = params.supported_types?.map((v)=>(v=='*' ? '' : `.${v}`))?.join(','); + fileEle.setAttribute('type', 'file'); + fileEle.setAttribute('accept', accept); + fileEle.onchange = (e)=>{ + if(e.target.value) { + onOK?.(e.target.value); + } else { + onCancel?.(); + } + }; + if(params.dialog_type == 'create_file') { + fileEle.setAttribute('nwsaveas', ''); + } else if(params.dialog_type == 'select_folder') { + fileEle.setAttribute('nwdirectory', ''); + } + fileEle.dispatchEvent(new MouseEvent('click')); + } + + show(params, onOK, onCancel, modalObj) { + let {name: browser} = getBrowser(); + if(browser == 'Nwjs') { + try { + this.showNative(params, onOK, onCancel); + } catch { + // Fall back to internal + this.showInternal(params, onOK, onCancel, modalObj); + } + } else { + // Fall back to internal + this.showInternal(params, onOK, onCancel, modalObj); + } + } +} diff --git a/web/pgadmin/misc/file_manager/static/js/components/FileManager.jsx b/web/pgadmin/misc/file_manager/static/js/components/FileManager.jsx new file mode 100644 index 000000000..2a75b2733 --- /dev/null +++ b/web/pgadmin/misc/file_manager/static/js/components/FileManager.jsx @@ -0,0 +1,770 @@ +import { Box, makeStyles } from '@material-ui/core'; +import React, { useCallback, useEffect, useMemo, useRef, useState } from 'react'; +import { DefaultButton, PgButtonGroup, PgIconButton, PrimaryButton } from '../../../../../static/js/components/Buttons'; +import { useModalStyles } from '../../../../../static/js/helpers/ModalProvider'; +import CloseIcon from '@material-ui/icons/CloseRounded'; +import CheckRoundedIcon from '@material-ui/icons/CheckRounded'; +import HomeRoundedIcon from '@material-ui/icons/HomeRounded'; +import ArrowUpwardRoundedIcon from '@material-ui/icons/ArrowUpwardRounded'; +import MoreHorizRoundedIcon from '@material-ui/icons/MoreHorizRounded'; +import SyncRoundedIcon from '@material-ui/icons/SyncRounded'; +import CreateNewFolderRoundedIcon from '@material-ui/icons/CreateNewFolderRounded'; +import GetAppRoundedIcon from '@material-ui/icons/GetAppRounded'; +import gettext from 'sources/gettext'; +import clsx from 'clsx'; +import { FormFooterMessage, InputSelectNonSearch, InputText, MESSAGE_TYPE } from '../../../../../static/js/components/FormComponents'; +import ListView from './ListView'; +import { PgMenu, PgMenuDivider, PgMenuItem, usePgMenuGroup } from '../../../../../static/js/components/Menu'; +import getApiInstance, { parseApiError } from '../../../../../static/js/api_instance'; +import Loader from 'sources/components/Loader'; +import url_for from 'sources/url_for'; +import Uploader from './Uploader'; +import GridView from './GridView'; +import convert from 'convert-units'; +import PropTypes from 'prop-types'; +import { downloadBlob } from '../../../../../static/js/utils'; +import ErrorBoundary from '../../../../../static/js/helpers/ErrorBoundary'; + + +const useStyles = makeStyles((theme)=>({ + footerSaveAs: { + justifyContent: 'initial', + padding: '4px 8px', + display: 'flex', + alignItems: 'center', + }, + footer1: { + justifyContent: 'space-between', + padding: '4px 8px', + display: 'flex', + alignItems: 'center', + }, + toolbar: { + padding: '4px', + display: 'flex', + ...theme.mixins.panelBorder?.bottom, + }, + inputFilename: { + lineHeight: 1, + width: '100%', + }, + inputSearch: { + marginLeft: '4px', + lineHeight: 1, + width: '130px', + }, + formatSelect: { + '& .MuiSelect-select': { + paddingTop: '4px', + paddingBottom: '4px', + } + }, + replaceOverlay: { + position: 'absolute', + top: 0, + bottom: 0, + left: 0, + right: 0, + backgroundColor: theme.otherVars.loader.backgroundColor, + zIndex: 2, + display: 'flex', + }, + replaceDialog: { + margin: 'auto', + marginLeft: '1rem', + marginRight: '1rem', + color: theme.palette.text.primary, + backgroundColor: theme.palette.background.default, + width: '100%', + ...theme.mixins.panelBorder.all, + } +})); + +export function getComparator(sortColumn) { + const key = sortColumn?.columnKey; + const dir = sortColumn?.direction == 'ASC' ? 1 : -1; + switch (key) { + case 'Filename': + return (a, b) => { + return dir*(a['Filename'].localeCompare(b['Filename'])); + }; + case 'Properties.DateModified': + return (a, b) => { + try { + let a1 = new Date(a['Properties']['Date Modified']); + let b1 = new Date(b['Properties']['Date Modified']); + if(a1 > b1) return dir*1; + return dir*(a1 < b1 ? -1 : 0); + } catch { + return 0; + } + }; + case 'Properties.Size': + return (a, b) => { + const parseAndConvert = (columnVal)=>{ + if(columnVal.file_type != 'dir' && columnVal.file_type != 'drive' && columnVal['Properties']['Size']) { + let [size, unit] = columnVal['Properties']['Size'].split(' '); + return convert(size).from(unit.toUpperCase()).to('B'); + } + return -1; + }; + try { + let a1 = parseAndConvert(a); + let b1 = parseAndConvert(b); + if(a1 > b1) return dir*1; + return dir*(a1 < b1 ? -1 : 0); + } catch { + return 0; + } + }; + default: + return ()=>0; + } +} + +export class FileManagerUtils { + constructor(api, params) { + this.api = api; + this.params = params; + this.config = {}; + this.currPath = ''; + this.separator = '/'; + } + + get transId() { + return this.config.transId; + } + + get fileConnectorUrl() { + return `${url_for('file_manager.index')}filemanager/${this.transId}/`; + } + + get fileRoot() { + return this.config.options.fileRoot; + } + + get allowedFileTypes() { + return this.config.options?.allowed_file_types || []; + } + + get showHiddenFiles() { + return this.config.options?.show_hidden_files; + } + + set showHiddenFiles(val) { + this.config.options.show_hidden_files = val; + this.api.put(url_for('file_manager.save_show_hidden_file_option', { + trans_id: this.transId, + }), { + show_hidden: val, + }).catch((error)=>{ + console.error(error); + /* Do nothing */ + }); + } + + hasCapability(val) { + return this.config?.options?.capabilities?.includes(val); + } + + async initialize() { + let res = await this.api.post(url_for('file_manager.init'), this.params); + this.config = res.data.data; + if(this.config.options.platform_type == 'win32') { + this.separator = '\\'; + } + } + + join(path1, path2) { + if(path1.endsWith(this.separator)) { + return path1 + path2; + } + return path1 + this.separator + path2; + } + + getExt(filename) { + if (filename.split('.').length == 1) { + return ''; + } + return filename.split('.').pop(); + } + + async getFolder(path) { + const newPath = path || this.fileRoot; + let res = await this.api.post(this.fileConnectorUrl, { + 'path': newPath, + 'mode': 'getfolder', + 'file_type': this.config.options.last_selected_format || '*', + 'show_hidden': this.showHiddenFiles, + }); + this.currPath = newPath; + return res.data.data.result; + } + + async addFolder(row) { + let res = await this.api.post(this.fileConnectorUrl, { + 'path': this.currPath, + 'mode': 'addfolder', + 'name': row.Filename, + }); + return { + Filename: res.data.data.result.Name, + Path: res.data.data.result.Path, + file_type: 'dir', + Properties: { + 'Date Modified': res.data.data.result['Date Modified'], + } + }; + } + + async renameItem(row) { + let res = await this.api.post(this.fileConnectorUrl, { + 'mode': 'rename', + 'old': row.Path, + 'new': row.Filename, + }); + return { + ...row, + Path: res.data.data.result['New Path'], + Filename: res.data.data.result['New Name'], + }; + } + + async deleteItem(row, fileName) { + const path = fileName ? this.join(row.Path, fileName) : row.Path; + await this.api.post(this.fileConnectorUrl, { + 'mode': 'delete', + 'path': path, + }); + return path; + } + + async uploadItem(fileObj, onUploadProgress) { + const formData = new FormData(); + formData.append('newfile', fileObj); + formData.append('mode', 'add'); + formData.append('currentpath', this.join(this.currPath, '')); + return this.api({ + method: 'POST', + url: this.fileConnectorUrl, + headers: { 'Content-Type': 'multipart/form-data' }, + data: formData, + onUploadProgress: onUploadProgress, + maxContentLength: Infinity, + maxBodyLength: Infinity, + }); + } + + async setLastVisitedDir(path) { + return this.api.post(url_for('file_manager.save_last_dir', { + trans_id: this.transId, + }), { + 'path': path, + }); + } + + async downloadFile(row) { + let res = await this.api({ + method: 'POST', + url: this.fileConnectorUrl, + responseType: 'blob', + data: { + 'mode': 'download', + 'path': row.Path, + }, + }); + downloadBlob(res.data, res.headers.filename); + } + + setDialogView(view) { + this.config.options.defaultViewMode = view; + this.api.post(url_for('file_manager.save_file_dialog_view', { + trans_id: this.transId, + }), {view: view}) + .catch((err)=>{ + /* Do not fail anything */ + console.error(err); + }); + } + + setFileType(fileType) { + this.config.options.last_selected_format = fileType; + this.api.post(url_for('settings.save_file_format_setting'), this.config.options) + .catch((err)=>{ + /* Do not fail anything */ + console.error(err); + }); + } + + async checkPermission(path) { + let res = await this.api.post(this.fileConnectorUrl, { + 'path': path, + 'mode': 'permission', + }); + if (res.data.data.result.Code === 1) { + return null; + } else { + return res.data.data.result.Error; + } + } + + async isFileExists(path, fileName) { + let res = await this.api.post(this.fileConnectorUrl, { + 'path': path, + 'name': fileName, + 'mode': 'is_file_exist', + }); + return Boolean(res.data.data.result.Code); + } + + async destroy() { + await this.api.delete(url_for('file_manager.delete_trans_id', { + 'trans_id': this.transId, + })); + } + + isWinDrive(text) { + return text && text.length == 2 && text.endsWith(':') && this.config?.options?.platform_type == 'win32'; + } + + dirname(path) { + let ret = path; + if(!path) { + return ret; + } + if(path.endsWith(this.separator)) { + ret = ret.slice(0, -1); + } + if(this.isWinDrive(ret)) { + ret = this.separator; + } else { + ret = ret.slice(0, ret.lastIndexOf(this.separator)+1); + } + return ret; + } +} + +function ConfirmFile({text, onYes, onNo}) { + const classes = useStyles(); + const modalClasses = useModalStyles(); + return ( + + + {text}{} + + } onClick={onNo} >{gettext('No')} + } + onClick={onYes} autoFocus>{gettext('Yes')} + + + + ); +} +ConfirmFile.propTypes = { + text: PropTypes.string, + onYes: PropTypes.func, + onNo: PropTypes.func +}; + +export default function FileManager({params, closeModal, onOK, onCancel}) { + const classes = useStyles(); + const modalClasses = useModalStyles(); + const apiObj = useMemo(()=>getApiInstance(), []); + const fmUtilsObj = useMemo(()=>new FileManagerUtils(apiObj, params), []); + + const {openMenuName, toggleMenu, onMenuClose} = usePgMenuGroup(); + const [loaderText, setLoaderText] = useState('Loading...'); + const [items, setItems] = useState([]); + const [path, setPath] = useState(''); + const [errorMsg, setErrorMsg] = useState(''); + const [search, setSearch] = useState(''); + const [saveAs, setSaveAs] = useState(''); + const [okBtnDisable, setOkBtnDisable] = useState(true); + const [viewMode, setViewMode] = useState('list'); + const [showUploader, setShowUploader] = useState(false); + const [[confirmText, onConfirmYes], setConfirmFile] = useState([null, null]); + const [fileType, setFileType] = useState('*'); + const [sortColumns, setSortColumns] = useState([]); + const [selectedRow, setSelectedRow] = useState(); + const selectedRowIdx = useRef(); + const optionsRef = React.useRef(null); + const saveAsRef = React.useRef(null); + const [operation, setOperation] = useState({ + type: null, idx: null + }); + + const sortedItems = useMemo(()=>( + [...items].sort(getComparator(sortColumns[0])) + ), [items, sortColumns]); + + const filteredItems = useMemo(()=>{ + return sortedItems.filter((i)=>i.Filename?.toLowerCase().includes(search?.toLocaleLowerCase())); + }, [items, sortColumns, search]); + + const itemsText = useMemo(()=>{ + let suffix = items.length == 1 ? 'item' : 'items'; + if(items.length == filteredItems.length) { + return `${items.length} ${suffix}`; + } + return `${filteredItems.length} of ${items.length} ${suffix}`; + }, [items, filteredItems]); + + const openDir = async (dirPath)=>{ + setErrorMsg(''); + setLoaderText('Loading...'); + try { + if(fmUtilsObj.isWinDrive(dirPath)) { + dirPath += fmUtilsObj.separator; + } + let newItems = await fmUtilsObj.getFolder(dirPath || fmUtilsObj.currPath); + setItems(newItems); + setPath(fmUtilsObj.currPath); + params.dialog_type == 'storage_dialog' && fmUtilsObj.setLastVisitedDir(fmUtilsObj.currPath); + } catch (error) { + console.error(error); + setErrorMsg(parseApiError(error)); + } + setLoaderText(''); + }; + const completeOperation = async (oldRow, newRow, rowIdx, func)=>{ + setOperation({}); + if(oldRow?.Filename == newRow.Filename) { + setItems((prev)=>[ + ...prev.slice(0, rowIdx), + oldRow, + ...prev.slice(rowIdx+1) + ]); + return; + } + setItems((prev)=>[ + ...prev.slice(0, rowIdx), + newRow, + ...prev.slice(rowIdx+1) + ]); + try { + const actualRow = await func(newRow); + setItems((prev)=>[ + ...prev.slice(0, rowIdx), + actualRow, + ...prev.slice(rowIdx+1) + ]); + } catch (error) { + setErrorMsg(parseApiError(error)); + if(oldRow) { + setItems((prev)=>[ + ...prev.slice(0, rowIdx), + oldRow, + ...prev.slice(rowIdx+1) + ]); + } else { + setItems((prev)=>[ + ...prev.slice(0, rowIdx), + ...prev.slice(rowIdx+1) + ]); + } + } + }; + const onDownload = async ()=>{ + setLoaderText('Downloading...'); + try { + await fmUtilsObj.downloadFile(filteredItems[selectedRowIdx.current]); + } catch (error) { + setErrorMsg(parseApiError(error)); + console.error(error); + } + setLoaderText(''); + }; + const onAddFolder = ()=>{ + setItems((prev)=>[ + {Filename: 'Untitled Folder', file_type: 'dir'}, + ...prev, + ]); + setOperation({ + type: 'add', + idx: 0, + onComplete: async (row, rowIdx)=>{ + setErrorMsg(''); + setLoaderText('Creating folder...'); + await completeOperation(null, row, rowIdx, fmUtilsObj.addFolder.bind(fmUtilsObj)); + setLoaderText(''); + } + }); + }; + const renameSelectedItem = (e)=>{ + e.keepOpen = false; + setErrorMsg(''); + if(_.isUndefined(selectedRowIdx.current) || _.isNull(selectedRowIdx.current)) { + return; + } + setOperation({ + type: 'rename', + idx: selectedRowIdx.current, + onComplete: async (row, rowIdx)=>{ + setErrorMsg(''); + setLoaderText('Renaming...'); + let oldRow = items[rowIdx]; + await completeOperation(oldRow, row, rowIdx, fmUtilsObj.renameItem.bind(fmUtilsObj)); + setLoaderText(''); + } + }); + }; + const deleteSelectedItem = async (e)=>{ + e.keepOpen = false; + setErrorMsg(''); + if(_.isUndefined(selectedRowIdx.current) || _.isNull(selectedRowIdx.current)) { + return; + } + setConfirmFile([gettext('Are you sure you want to delete this file/folder?'), async ()=>{ + setConfirmFile([null, null]); + setLoaderText('Deleting...'); + try { + await fmUtilsObj.deleteItem(items[selectedRowIdx.current]); + setItems((prev)=>[ + ...prev.slice(0, selectedRowIdx.current), + ...prev.slice(selectedRowIdx.current+1), + ]); + } catch (error) { + setErrorMsg(parseApiError(error)); + console.error(error); + } + setLoaderText(''); + }]); + }; + const toggleViewMode = (e, val)=>{ + e.keepOpen = false; + setViewMode(val); + fmUtilsObj.setDialogView(val); + }; + const onOkClick = useCallback(async ()=>{ + setLoaderText('Please wait...'); + let onOkPath = null; + if(params.dialog_type == 'create_file') { + let newFileName = saveAs; + // Add the extension if user has not added. + if(fileType != '*' && !newFileName.endsWith(`.${fileType}`)) { + newFileName += `.${fileType}`; + } + onOkPath = fmUtilsObj.join(fmUtilsObj.currPath, newFileName); + let error = await fmUtilsObj.checkPermission(onOkPath); + if(error) { + setErrorMsg(error); + setLoaderText(''); + return; + } + let exists = await fmUtilsObj.isFileExists(fmUtilsObj.currPath, newFileName); + if(exists) { + setLoaderText(''); + setConfirmFile([gettext('Are you sure you want to replace this file?'), async ()=>{ + await fmUtilsObj.setLastVisitedDir(fmUtilsObj.currPath); + onOK?.(onOkPath); + closeModal(); + }]); + return; + } + } else if(selectedRowIdx?.current >= 0 && filteredItems[selectedRowIdx?.current]) { + onOkPath = filteredItems[selectedRowIdx?.current]['Path']; + } + await fmUtilsObj.setLastVisitedDir(fmUtilsObj.currPath); + onOK?.(onOkPath); + closeModal(); + }, [filteredItems, saveAs, fileType]); + const onItemEnter = useCallback(async (row)=>{ + if(row.file_type == 'dir' || row.file_type == 'drive') { + await openDir(row.Path); + } else { + if(params.dialog_type == 'select_file') { + onOkClick(); + } + } + }, [filteredItems]); + const onItemSelect = useCallback((idx)=>{ + selectedRowIdx.current = idx; + fewBtnDisableCheck(); + }, [filteredItems]); + const onItemClick = useCallback((idx)=>{ + let row = filteredItems[selectedRowIdx.current]; + if(params.dialog_type == 'create_file' && row?.file_type != 'dir' && row.file_type != 'drive') { + setSaveAs(filteredItems[idx]?.Filename); + } + }, [filteredItems]); + const fewBtnDisableCheck = ()=>{ + let disabled = true; + let row = filteredItems[selectedRowIdx.current]; + if(params.dialog_type == 'create_file') { + disabled = !saveAs.trim(); + } else if(selectedRowIdx.current >= 0 && row) { + let selectedfileType = row?.file_type; + if(((selectedfileType == 'dir' || selectedfileType == 'drive') && fmUtilsObj.hasCapability('select_folder')) + || (selectedfileType != 'dir' && selectedfileType != 'drive' && fmUtilsObj.hasCapability('select_file'))) { + disabled = false; + } + } + setOkBtnDisable(disabled); + setSelectedRow(row); + }; + useEffect(()=>{ + const init = async ()=>{ + await fmUtilsObj.initialize(); + if(params.dialog_type != 'select_folder') { + setFileType(fmUtilsObj.config?.options?.last_selected_format || '*'); + } + if(fmUtilsObj.config?.options?.defaultViewMode) { + setViewMode(fmUtilsObj.config?.options?.defaultViewMode); + } else { + setViewMode('list'); + } + openDir(params?.path); + params?.path && fmUtilsObj.setLastVisitedDir(params?.path); + }; + init(); + setTimeout(()=>{ + saveAsRef.current && saveAsRef.current.focus(); + }, 300); + return ()=>{ + fmUtilsObj.destroy(); + }; + }, []); + + useEffect(()=>{ + fewBtnDisableCheck(); + }, [saveAs, filteredItems.length]); + + const isNoneSelected = _.isUndefined(selectedRow); + let okBtnText = params.btn_primary; + if(!okBtnText) { + okBtnText = gettext('Select'); + if(params.dialog_type == 'create_file' || params.dialog_type == 'create_folder') { + okBtnText = gettext('Create'); + } + } + return ( + + + + + {Boolean(confirmText) && setConfirmFile([null, null])} onYes={onConfirmYes}/>} + + + { + await openDir(fmUtilsObj.config?.options?.homedir); + }} icon={} disabled={showUploader} /> + { + await openDir(fmUtilsObj.dirname(fmUtilsObj.currPath)); + }} icon={} disabled={!fmUtilsObj.dirname(fmUtilsObj.currPath) || showUploader} /> + { + if(e.code === 'Enter') { + e.preventDefault(); + await openDir(path); + } + }} value={path} onChange={setPath} readonly={showUploader} /> + { + await openDir(); + }} icon={} disabled={showUploader} /> + + + + {params.dialog_type == 'storage_dialog' && + } + onClick={onDownload} disabled={showUploader || isNoneSelected || selectedRow?.file_type == 'dir' || selectedRow?.file_type == 'drive'} />} + {fmUtilsObj.hasCapability('create') && } + onClick={onAddFolder} disabled={showUploader} />} + + + } + name="menu-options" ref={optionsRef} onClick={toggleMenu} disabled={showUploader} /> + + + {fmUtilsObj.hasCapability('rename') && + {gettext('Rename')} + } + {fmUtilsObj.hasCapability('delete') && + {gettext('Delete')} + } + {fmUtilsObj.hasCapability('upload') && <> + + { + e.keepOpen = false; + setShowUploader(true); + }}>{gettext('Upload')} + } + + toggleViewMode(e, 'list')}>{gettext('List View')} + toggleViewMode(e, 'grid')}>{gettext('Grid View')} + + { + e.keepOpen = false; + fmUtilsObj.showHiddenFiles = !fmUtilsObj.showHiddenFiles; + await openDir(); + }}>{gettext('Show Hidden Files')} + + + + {showUploader && + { + setShowUploader(false); + if(filesUploaded) { + await openDir(); + } + }}/>} + {viewMode == 'list' && + } + {viewMode == 'grid' && + } + setErrorMsg('')} /> + {params.dialog_type == 'create_file' && + + Save As + + } + {params.dialog_type != 'select_folder' && + + {itemsText} + + File Format + { + let val = e.target.value; + fmUtilsObj.setFileType(val); + openDir(fmUtilsObj.currPath); + setFileType(val); + }} + options={fmUtilsObj.allowedFileTypes?.map((type)=>({ + label: type == '*' ? gettext('All Files') : type, value: type + }))} /> + + } + + + + + + } onClick={()=>{ + onCancel?.(); + closeModal(); + }} >{gettext('Cancel')} + {params.dialog_type != 'storage_dialog' && + } + onClick={onOkClick} disabled={okBtnDisable || showUploader}>{okBtnText}} + + + + ); +} + +FileManager.propTypes = { + params: PropTypes.object, + closeModal: PropTypes.func, + onOK: PropTypes.func, + onCancel: PropTypes.func, +}; diff --git a/web/pgadmin/misc/file_manager/static/js/components/FileManagerConstants.js b/web/pgadmin/misc/file_manager/static/js/components/FileManagerConstants.js new file mode 100644 index 000000000..657bf66f5 --- /dev/null +++ b/web/pgadmin/misc/file_manager/static/js/components/FileManagerConstants.js @@ -0,0 +1,11 @@ +///////////////////////////////////////////////////////////// +// +// pgAdmin 4 - PostgreSQL Tools +// +// Copyright (C) 2013 - 2022, The pgAdmin Development Team +// This software is released under the PostgreSQL Licence +// +////////////////////////////////////////////////////////////// +export const FILE_MANGER_EVENTS = { + ADD_FOLDER: 'ADD_FOLDER' +}; diff --git a/web/pgadmin/misc/file_manager/static/js/components/GridView.jsx b/web/pgadmin/misc/file_manager/static/js/components/GridView.jsx new file mode 100644 index 000000000..39254aeae --- /dev/null +++ b/web/pgadmin/misc/file_manager/static/js/components/GridView.jsx @@ -0,0 +1,141 @@ +import { Box, makeStyles } from '@material-ui/core'; +import React, {useState, useEffect, useRef, useLayoutEffect} from 'react'; +import FolderIcon from '@material-ui/icons/Folder'; +import DescriptionIcon from '@material-ui/icons/Description'; +import LockRoundedIcon from '@material-ui/icons/LockRounded'; +import StorageRoundedIcon from '@material-ui/icons/StorageRounded'; +import PropTypes from 'prop-types'; + + +const useStyles = makeStyles((theme)=>({ + grid: { + display: 'flex', + fontSize: '13px', + flexWrap: 'wrap', + overflow: 'hidden', + }, + gridItem: { + width: '100px', + margin: '4px', + textAlign: 'center', + position: 'relative', + }, + gridItemContent: { + padding: '4px', + border: '1px solid transparent', + cursor: 'pointer', + '&[aria-selected=true]': { + backgroundColor: theme.palette.primary.light, + color: theme.otherVars.qtDatagridSelectFg, + borderColor: theme.palette.primary.main, + }, + }, + gridFilename: { + overflowWrap: 'break-word', + }, + gridItemEdit: { + border: `1px solid ${theme.otherVars.inputBorderColor}`, + backgroundColor: theme.palette.background.default, + }, + protected: { + height: '1.25rem', + width: '1.25rem', + position: 'absolute', + left: '52px', + color: theme.palette.error.main, + backgroundColor: 'inherit', + } +})); + +export function ItemView({idx, row, selected, onItemSelect, onItemEnter, onEditComplete}) { + const classes = useStyles(); + const editMode = Boolean(onEditComplete); + const fileNameRef = useRef(); + + useLayoutEffect(()=>{ + if(editMode) { + fileNameRef.current?.focus(); + } + }, [editMode]); + + const handleKeyDown = (e)=>{ + if(e.code == 'Tab') { + e.stopPropagation(); + } + if(e.code == 'Enter') { + onEditComplete({...row, Filename: fileNameRef.current.textContent?.trim()}); + } + if(e.code == 'Escape') { + e.preventDefault(); + e.stopPropagation(); + fileNameRef.current.textContent = row.Filename; + onEditComplete(row); + } + }; + + let icon = ; + if(row.file_type == 'dir') { + icon = ; + } else if(row.file_type == 'drive') { + icon = ; + } + + return ( +
  • +
    onItemSelect(idx)} onDoubleClick={()=>onItemEnter(row)}> +
    + {icon} + {Boolean(row.Protected) && } +
    +
    onEditComplete(row)} + className={editMode ? classes.gridItemEdit : classes.gridFilename} suppressContentEditableWarning={true} + contentEditable={editMode} data-test="filename-div">{row['Filename']}
    +
    +
  • + ); +} +ItemView.propTypes = { + idx: PropTypes.number, + row: PropTypes.object, + selected: PropTypes.bool, + onItemSelect: PropTypes.func, + onItemEnter: PropTypes.func, + onEditComplete: PropTypes.func, +}; + +export default function GridView({items, operation, onItemSelect, onItemEnter}) { + const classes = useStyles(); + const [selectedIdx, setSelectedIdx] = useState(null); + const gridRef = useRef(); + + useEffect(()=>{ + onItemSelect(selectedIdx); + }, [selectedIdx]); + + + let onEditComplete = null; + if(operation?.onComplete) { + onEditComplete = (row)=>{ + operation?.onComplete?.(row, operation.idx); + }; + } + + return ( + +
      + {items.map((item, i)=>( + ) + )} +
    + {items.length == 0 && No files/folders found} +
    + ); +} + +GridView.propTypes = { + items: PropTypes.arrayOf(PropTypes.object), + operation: PropTypes.object, + onItemSelect: PropTypes.func, + onItemEnter: PropTypes.func, +}; diff --git a/web/pgadmin/misc/file_manager/static/js/components/ListView.jsx b/web/pgadmin/misc/file_manager/static/js/components/ListView.jsx new file mode 100644 index 000000000..f8879be9a --- /dev/null +++ b/web/pgadmin/misc/file_manager/static/js/components/ListView.jsx @@ -0,0 +1,239 @@ +import { Box, makeStyles } from '@material-ui/core'; +import React, { useContext, useRef, useEffect } from 'react'; +import { Row } from 'react-data-grid'; +import PgReactDataGrid from '../../../../../static/js/components/PgReactDataGrid'; +import FolderIcon from '@material-ui/icons/Folder'; +import StorageRoundedIcon from '@material-ui/icons/StorageRounded'; +import DescriptionIcon from '@material-ui/icons/Description'; +import LockRoundedIcon from '@material-ui/icons/LockRounded'; +import KeyboardArrowUpIcon from '@material-ui/icons/KeyboardArrowUp'; +import KeyboardArrowDownIcon from '@material-ui/icons/KeyboardArrowDown'; +import PropTypes from 'prop-types'; + +const useStyles = makeStyles((theme)=>({ + grid: { + fontSize: '13px', + '& .rdg-header-row': { + '& .rdg-cell': { + padding: '0px 4px', + } + }, + '& .rdg-cell': { + padding: '0px 4px', + '&[aria-colindex="1"]': { + padding: '0px 4px', + '&.rdg-editor-container': { + padding: '0px', + }, + } + } + }, + input: { + appearance: 'none', + width: '100%', + height: '100%', + verticalAlign: 'top', + outline: 'none', + backgroundColor: theme.palette.background.default, + color: theme.palette.text.primary, + border: 0, + boxShadow: 'inset 0 0 0 1.5px '+theme.palette.primary.main, + padding: '0 2px', + '::selection': { + background: theme.palette.primary.light, + } + }, + protected: { + height: '0.75rem', + width: '0.75rem', + position: 'absolute', + left: '14px', + top: '5px', + color: theme.palette.error.main, + backgroundColor: 'inherit', + } +})); + +export const GridContextUtils = React.createContext(); + +export function FileNameEditor({row, column, onRowChange, onClose}) { + const classes = useStyles(); + const value = row[column.key] ?? ''; + const [localVal, setLocalVal] = React.useState(value); + const localValRef = useRef(localVal); + + localValRef.current = localVal; + useEffect(()=>{ + return ()=>{ + /* When unmounted, trigger onRowChange */ + onRowChange({ ...row, [column.key]: localValRef.current?.trim()}, true); + }; + }, []); + + const onKeyDown = (e)=>{ + if(e.code === 'Tab' || e.code === 'Enter') { + e.preventDefault(); + onClose(); + } + }; + return ( + { + setLocalVal(e.target.value); + }} + onKeyDown={onKeyDown} + autoFocus + /> + ); +} + +FileNameEditor.propTypes = { + row: PropTypes.object, + column: PropTypes.object, + onRowChange: PropTypes.func, + onClose: PropTypes.func, +}; + +function CutomSortIcon({sortDirection}) { + if(sortDirection == 'DESC') { + return ; + } else if(sortDirection == 'ASC') { + return ; + } + return <>; +} +CutomSortIcon.propTypes = { + sortDirection: PropTypes.string, +}; + +export function CustomRow({inTest=false, ...props}) { + const gridUtils = useContext(GridContextUtils); + const handleKeyDown = (e)=>{ + if(e.code == 'Tab' || e.code == 'ArrowRight' || e.code == 'ArrowLeft') { + e.stopPropagation(); + } + if(e.code == 'Enter') { + gridUtils.onItemEnter(props.row); + } + }; + const isRowSelected = props.selectedCellIdx >= 0; + useEffect(()=>{ + if(isRowSelected) { + gridUtils.onItemSelect(props.rowIdx); + } + }, [props.selectedCellIdx]); + if(inTest) { + return
    ; + } + const onRowClick = (...args)=>{ + gridUtils.onItemClick?.(props.rowIdx); + props.onRowClick?.(...args); + }; + return ( + gridUtils.onItemEnter(row)} + selectCell={(row, column)=>props.selectCell(row, column)} aria-selected={isRowSelected}/> + ); +} +CustomRow.propTypes = { + inTest: PropTypes.bool, + row: PropTypes.object, + selectedCellIdx: PropTypes.number, + onRowClick: PropTypes.func, + rowIdx: PropTypes.number, + selectCell: PropTypes.func, +}; + +function FileNameFormatter({row}) { + const classes = useStyles(); + let icon = ; + if(row.file_type == 'dir') { + icon = ; + } else if(row.file_type == 'drive') { + icon = ; + } + return <> + {icon} + {Boolean(row.Protected) && } + {row['Filename']} + ; +} +FileNameFormatter.propTypes = { + row: PropTypes.object, +}; + +const columns = [ + { + key: 'Filename', + name: 'Name', + formatter: FileNameFormatter, + editor: FileNameEditor, + editorOptions: { + editOnClick: false, + onCellKeyDown: (e)=>e.preventDefault(), + } + },{ + key: 'Properties.DateModified', + name: 'Date Modified', + formatter: ({row})=><>{row.Properties?.['Date Modified']} + },{ + key: 'Properties.Size', + name: 'Size', + formatter: ({row})=><>{row.file_type != 'dir' && row.Properties?.['Size']} + } +]; + + +export default function ListView({items, operation, onItemSelect, onItemEnter, onItemClick, ...props}) { + const classes = useStyles(); + const gridRef = useRef(); + + useEffect(()=>{ + if(operation.type) { + operation.type == 'add' && gridRef.current.scrollToRow(operation.idx); + gridRef.current.selectCell({idx: 0, rowIdx: operation.idx}, true); + } + }, [operation]); + + useEffect(()=>{ + gridRef.current.selectCell({idx: 0, rowIdx: 0}); + }, [gridRef.current?.element]); + + return ( + + No files/folders found, + }} + onRowsChange={(rows)=>{ + operation?.onComplete?.(rows[operation.idx], operation.idx); + }} + {...props} + /> + + ); +} +ListView.propTypes = { + items: PropTypes.arrayOf(PropTypes.object), + operation: PropTypes.object, + onItemSelect: PropTypes.func, + onItemEnter: PropTypes.func, + onItemClick: PropTypes.func, +}; diff --git a/web/pgadmin/misc/file_manager/static/js/components/Uploader.jsx b/web/pgadmin/misc/file_manager/static/js/components/Uploader.jsx new file mode 100644 index 000000000..f03223424 --- /dev/null +++ b/web/pgadmin/misc/file_manager/static/js/components/Uploader.jsx @@ -0,0 +1,197 @@ +import React, { useCallback, useReducer, useEffect, useMemo } from 'react'; +import { Box, List, ListItem, makeStyles } from '@material-ui/core'; +import CloseIcon from '@material-ui/icons/CloseRounded'; +import { PgIconButton } from '../../../../../static/js/components/Buttons'; +import gettext from 'sources/gettext'; +import {useDropzone} from 'react-dropzone'; +import { FormFooterMessage, MESSAGE_TYPE } from '../../../../../static/js/components/FormComponents'; +import convert from 'convert-units'; +import _ from 'lodash'; +import PropTypes from 'prop-types'; + +const useStyles = makeStyles((theme)=>({ + root: { + position: 'absolute', + top: 0, + bottom: 0, + left: 0, + right: 0, + zIndex: 1, + backgroundColor: theme.palette.background.default, + display: 'flex', + flexDirection: 'column', + padding: '4px', + }, + uploadArea: { + border: `1px dashed ${theme.palette.grey[600]}`, + display: 'flex', + alignItems: 'center', + justifyContent: 'center', + flexGrow: 1, + flexDirection: 'column', + cursor: 'move', + textAlign: 'center', + padding: '4px', + }, + uploadFilesRoot: { + width: '350px', + border: `1px dashed ${theme.palette.grey[600]}`, + borderLeft: 'none', + overflowX: 'hidden', + overflowY: 'auto' + }, + uploadProgress: { + position: 'unset', + padding: 0, + }, + uploadPending: { + + } +})); + +export function filesReducer(state, action) { + let newState = [...state]; + switch (action.type) { + case 'add': + newState.unshift(...action.files.map((file)=>({ + id: _.uniqueId('f'), + file: file, + progress: 0, + started: false, + failed: false, + done: false, + deleting: false, + }))); + break; + case 'started': + _.find(newState, (f)=>f.id==action.id).started = true; + break; + case 'progress': + _.find(newState, (f)=>f.id==action.id).progress = action.value; + break; + case 'failed': + _.find(newState, (f)=>f.id==action.id).failed = true; + break; + case 'done': + _.find(newState, (f)=>f.id==action.id).done = true; + break; + case 'remove': + newState = newState.filter((f)=>f.id!=action.id) || []; + break; + default: + break; + } + return newState; +} + +export function getFileSize(bytes) { + let conVal = convert(bytes).from('B').toBest(); + conVal.val = Math.round(conVal.val * 100) / 100; + return `${conVal.val} ${conVal.unit}`; +} + +export function UploadedFile({upfile, removeFile}) { + let type = MESSAGE_TYPE.INFO; + let message = `Uploading... ${upfile.progress?.toString() || ''}%`; + if(upfile.done) { + type = MESSAGE_TYPE.SUCCESS; + message = 'Uploaded!'; + } else if(upfile.failed) { + type = MESSAGE_TYPE.ERROR; + message = 'Failed!'; + } + + return ( + + + {upfile.file.name} + + } size="xs" noBorder onClick={removeFile} /> + + + {useMemo(()=>getFileSize(upfile.file.size), [])} + + + ); +} +UploadedFile.propTypes = { + upfile: PropTypes.object, + removeFile: PropTypes.func, +}; + + +export default function Uploader({fmUtilsObj, onClose}) { + const classes = useStyles(); + const [files, dispatchFileAction] = useReducer(filesReducer, []); + const onDrop = useCallback(acceptedFiles => { + dispatchFileAction({ + type: 'add', + files: acceptedFiles, + }); + }, []); + const {getRootProps, getInputProps} = useDropzone({onDrop}); + + useEffect(()=>{ + files.forEach(async (upfile)=>{ + if(!upfile.started && !upfile.failed) { + try { + dispatchFileAction({ + type: 'started', + id: upfile.id, + }); + await fmUtilsObj.uploadItem(upfile.file, (progressEvent)=>{ + const {loaded, total} = progressEvent; + const percent = Math.floor((loaded * 100) / total); + dispatchFileAction({ + type: 'progress', + id: upfile.id, + value: percent, + }); + }); + dispatchFileAction({ + type: 'done', + id: upfile.id, + }); + } catch { + dispatchFileAction({ + type: 'failed', + id: upfile.id, + }); + } + } + }); + }, [files.length]); + + return ( + + + } size="xs" noBorder onClick={onClose} /> + + + + + {gettext('Drop files here, or click to select files.')} + {gettext('The file size limit (per file) is %s MB.', fmUtilsObj.config?.upload?.fileSizeLimit)} + + {files.length > 0 && + + + {files.map((upfile)=>( + { + dispatchFileAction({ + type: 'remove', + id: upfile.id, + }); + }}/> + ))} + + } + + + ); +} +Uploader.propTypes = { + fmUtilsObj: PropTypes.object, + onClose: PropTypes.func, +}; diff --git a/web/pgadmin/misc/file_manager/static/js/create_dialogue.js b/web/pgadmin/misc/file_manager/static/js/create_dialogue.js deleted file mode 100644 index cdd9917e1..000000000 --- a/web/pgadmin/misc/file_manager/static/js/create_dialogue.js +++ /dev/null @@ -1,195 +0,0 @@ -///////////////////////////////////////////////////////////// -// -// pgAdmin 4 - PostgreSQL Tools -// -// Copyright (C) 2013 - 2022, The pgAdmin Development Team -// This software is released under the PostgreSQL Licence -// -////////////////////////////////////////////////////////////// - -import gettext from 'sources/gettext'; -import url_for from 'sources/url_for'; -import $ from 'jquery'; -import Alertify from 'pgadmin.alertifyjs'; -import pgAdmin from 'sources/pgadmin'; -import {removeTransId, set_last_traversed_dir} from './helpers'; -import Notify from '../../../../static/js/helpers/Notifier'; - -// Declare the Create mode dialog -module.exports = Alertify.dialog('createModeDlg', function() { - // Dialog property - return { - setup: function() { - return { - buttons: [{ - text: gettext('Cancel'), - key: 27, - className: 'btn btn-secondary fa fa-times file_manager_create_cancel pg-alertify-button', - },{ - text: gettext('Create'), - key: 13, - className: 'btn btn-primary fa fa-file file_manager_create file_manager_ok pg-alertify-button disabled', - }], - options: { - closableByDimmer: false, - maximizable: false, - closable: false, - movable: true, - padding: !1, - overflow: !1, - model: 0, - resizable: true, - pinnable: false, - modal: false, - autoReset: false, - }, - }; - }, - replace_file: function() { - var $yesBtn = $('.replace_file .btn_yes'), - $noBtn = $('.replace_file .btn_no'); - - $('.storage_dialog #uploader .input-path').attr('disabled', true); - $('.file_manager_ok').addClass('disabled'); - $('.replace_file, .fm_dimmer').show(); - - $yesBtn.on('click',() => { - $('.replace_file, .fm_dimmer').hide(); - $yesBtn.off(); - $noBtn.off(); - var newFile = $('.storage_dialog #uploader .input-path').val(); - - pgAdmin.Browser.Events.trigger('pgadmin-storage:finish_btn:create_file', newFile); - $('.file_manager_create_cancel').trigger('click'); - $('.storage_dialog #uploader .input-path').attr('disabled', false); - $('.file_manager_ok').removeClass('disabled'); - }); - - $noBtn.on('click',() => { - $('.replace_file, .fm_dimmer').hide(); - $yesBtn.off(); - $noBtn.off(); - $('.storage_dialog #uploader .input-path').attr('disabled', false); - $('.file_manager_ok').removeClass('disabled'); - }); - }, - is_file_exist: function() { - var full_path = $('.storage_dialog #uploader .input-path').val(), - path = full_path.substr(0, full_path.lastIndexOf('/') + 1), - selected_item = full_path.substr(full_path.lastIndexOf('/') + 1), - is_exist = false; - - var file_data = { - 'path': path, - 'name': selected_item, - 'mode': 'is_file_exist', - }; - - $.ajax({ - type: 'POST', - data: JSON.stringify(file_data), - url: url_for('file_manager.filemanager', { - 'trans_id': this.trans_id, - }), - dataType: 'json', - contentType: 'application/x-download; charset=utf-8', - async: false, - }) - .done(function(resp) { - var data = resp.data.result; - if (data['Code'] === 1) { - is_exist = true; - } else { - is_exist = false; - } - }); - return is_exist; - }, - check_permission: function(path) { - var permission = false, - post_data = { - 'path': path, - 'mode': 'permission', - }; - - $.ajax({ - type: 'POST', - data: JSON.stringify(post_data), - url: url_for('file_manager.filemanager', { - 'trans_id': this.trans_id, - }), - dataType: 'json', - contentType: 'application/json; charset=utf-8', - async: false, - }) - .done(function(resp) { - var data = resp.data.result; - if (data.Code === 1) { - permission = true; - } else { - $('.file_manager_ok').addClass('disabled'); - Notify.error(data.Error); - } - }) - .fail(function() { - $('.file_manager_ok').addClass('disabled'); - Notify.error(gettext('Error occurred while checking access permission.')); - }); - return permission; - }, - callback: function(closeEvent) { - closeEvent.cancel = false; - if (closeEvent.button.text == gettext('Create')) { - var act_variable = document.activeElement.id; - if(act_variable != 'refresh_list') { - var newFile = $('.storage_dialog #uploader .input-path').val(), - file_data = { - 'path': $('.currentpath').val(), - }, - innerbody, - ext = $('.allowed_file_types select').val(); - - /* - Add the file extension if necessary, and if the file type selector - isn't set to "All Files". If there's no . at all in the path, or - there is a . already but it's not following the last /, AND the - extension isn't *, then we add the extension. - */ - if ((!newFile.includes('.') || - newFile.split('.').pop() != ext) && - ext != '*') { - newFile = newFile + '.' + ext; - $('.storage_dialog #uploader .input-path').val(newFile); - } - - if (!this.check_permission(newFile)) { - closeEvent.cancel = true; - return; - } - - if (!_.isUndefined(newFile) && newFile !== '' && this.is_file_exist()) { - this.replace_file(); - this.$container.find('.replace_file').find('.btn_yes').trigger('focus'); - closeEvent.cancel = true; - } else { - pgAdmin.Browser.Events.trigger('pgadmin-storage:finish_btn:create_file', newFile); - innerbody = $(this.elements.body).find('.storage_content'); - $(innerbody).find('*').off(); - innerbody.remove(); - removeTransId(this.trans_id); - } - - set_last_traversed_dir(file_data, this.trans_id); - } else { - closeEvent.cancel = true; - } - } else if (closeEvent.button.text == gettext('Cancel')) { - innerbody = $(this.elements.body).find('.storage_content'); - $(innerbody).find('*').off(); - innerbody.remove(); - removeTransId(this.trans_id); - pgAdmin.Browser.Events.trigger('pgadmin-storage:cancel_btn:create_file'); - } - }, - }; -}, false, 'fileSelectionDlg'); diff --git a/web/pgadmin/misc/file_manager/static/js/file_manager.js b/web/pgadmin/misc/file_manager/static/js/file_manager.js deleted file mode 100644 index 0b4a33cc1..000000000 --- a/web/pgadmin/misc/file_manager/static/js/file_manager.js +++ /dev/null @@ -1,55 +0,0 @@ -///////////////////////////////////////////////////////////// -// -// pgAdmin 4 - PostgreSQL Tools -// -// Copyright (C) 2013 - 2022, The pgAdmin Development Team -// This software is released under the PostgreSQL Licence -// -////////////////////////////////////////////////////////////// - -import './select_dialogue'; -import './create_dialogue'; -import './storage_dialogue'; - -define('misc.file_manager', [ - 'sources/gettext', 'sources/url_for', 'jquery', 'underscore', - 'sources/pgadmin', 'pgadmin.alertifyjs', -], function(gettext, url_for, $, _, pgAdmin, Alertify) { - pgAdmin = pgAdmin || window.pgAdmin || {}; - - /* - * - * - * Hmm... this module is already been initialized, we can refer to the old - * object from here. - */ - if (pgAdmin.FileManager) { - return pgAdmin.FileManager; - } - - pgAdmin.FileManager = { - init: function() { - if (this.initialized) { - return; - } - - this.initialized = true; - - }, - // Call dialogs subject to dialog_type param - show_dialog: function(params) { - let dialogWidth = pgAdmin.Browser.stdW.calc(pgAdmin.Browser.stdW.md); - let dialogHeight = pgAdmin.Browser.stdH.calc(pgAdmin.Browser.stdH.lg); - if (params.dialog_type == 'create_file') { - Alertify.createModeDlg(params).resizeTo(dialogWidth, dialogHeight); - } else if(params.dialog_type == 'storage_dialog') { - Alertify.fileStorageDlg(params).resizeTo(dialogWidth, dialogHeight); - } - else { - Alertify.fileSelectionDlg(params).resizeTo(dialogWidth, dialogHeight); - } - }, - }; - - return pgAdmin.FileManager; -}); diff --git a/web/pgadmin/misc/file_manager/static/js/helpers.js b/web/pgadmin/misc/file_manager/static/js/helpers.js deleted file mode 100644 index af24bfa71..000000000 --- a/web/pgadmin/misc/file_manager/static/js/helpers.js +++ /dev/null @@ -1,47 +0,0 @@ -///////////////////////////////////////////////////////////// -// -// pgAdmin 4 - PostgreSQL Tools -// -// Copyright (C) 2013 - 2022, The pgAdmin Development Team -// This software is released under the PostgreSQL Licence -// -////////////////////////////////////////////////////////////// - -import url_for from 'sources/url_for'; -import $ from 'jquery'; - -// Send a request to get transaction id -export function getTransId(configs) { - return $.ajax({ - data: configs, - type: 'POST', - async: false, - url: url_for('file_manager.get_trans_id'), - dataType: 'json', - contentType: 'application/json; charset=utf-8', - }); -} - -// Function to remove trans id from session -export function removeTransId(trans_id) { - return $.ajax({ - type: 'GET', - async: false, - url: url_for('file_manager.delete_trans_id', { - 'trans_id': trans_id, - }), - dataType: 'json', - contentType: 'application/json; charset=utf-8', - }); -} - -export function set_last_traversed_dir(path, trans_id) { - return $.ajax({ - url: url_for('file_manager.save_last_dir', { - 'trans_id': trans_id, - }), - type: 'POST', - data: JSON.stringify(path), - contentType: 'application/json', - }); -} diff --git a/web/pgadmin/misc/file_manager/static/js/index.js b/web/pgadmin/misc/file_manager/static/js/index.js new file mode 100644 index 000000000..63ddc7629 --- /dev/null +++ b/web/pgadmin/misc/file_manager/static/js/index.js @@ -0,0 +1,25 @@ +///////////////////////////////////////////////////////////// +// +// pgAdmin 4 - PostgreSQL Tools +// +// Copyright (C) 2013 - 2022, The pgAdmin Development Team +// This software is released under the PostgreSQL Licence +// +////////////////////////////////////////////////////////////// +import pgAdmin from 'sources/pgadmin'; +import FileManagerModule from './FileManagerModule'; + +/* eslint-disable */ +/* This is used to change publicPath of webpack at runtime for loading chunks */ +/* Do not add let, var, const to this variable */ +__webpack_public_path__ = window.resourceBasePath; +/* eslint-enable */ + +if(!pgAdmin.Tools) { + pgAdmin.Tools = {}; +} +pgAdmin.Tools.FileManager = FileManagerModule.getInstance(pgAdmin); + +module.exports = { + FileManager: pgAdmin.Tools.FileManager, +}; diff --git a/web/pgadmin/misc/file_manager/static/js/select_dialogue.js b/web/pgadmin/misc/file_manager/static/js/select_dialogue.js deleted file mode 100644 index 74903e1cd..000000000 --- a/web/pgadmin/misc/file_manager/static/js/select_dialogue.js +++ /dev/null @@ -1,148 +0,0 @@ -///////////////////////////////////////////////////////////// -// -// pgAdmin 4 - PostgreSQL Tools -// -// Copyright (C) 2013 - 2022, The pgAdmin Development Team -// This software is released under the PostgreSQL Licence -// -////////////////////////////////////////////////////////////// - -import gettext from 'sources/gettext'; -import url_for from 'sources/url_for'; -import $ from 'jquery'; -import Alertify from 'pgadmin.alertifyjs'; -import pgAdmin from 'sources/pgadmin'; -import {getTransId, removeTransId, set_last_traversed_dir} from './helpers'; - -// Declare the Selection dialog -module.exports = Alertify.dialog('fileSelectionDlg', function() { - // Dialog property - return { - main: function(params) { - // Set title and button name - var self = this; - if (_.isUndefined(params['dialog_title'])) { - params['dialog_title'] = gettext('Select file'); - } - self.dialog_type = params['dialog_type']; - - this.set('title', params['dialog_title']); - this.params = JSON.stringify(params); - - this.show(); - - }, - settings: { - label: undefined, - }, - settingUpdated: function(key, oldValue, newValue) { - switch (key) { - case 'message': - this.setMessage(newValue); - break; - case 'label': - if (this.__internal.buttons[0].element) { - this.__internal.buttons[0].element.innerHTML = newValue; - } - break; - default: - break; - } - }, - prepare: function() { - var self = this; - - self.$container.find('.storage_content').remove(); - self.$container.append('
    '); - - var content = self.$container.find('.storage_content'); - content.empty(); - - // Add our class to alertify - $(this.elements.body.childNodes[0]).addClass('alertify_tools_dialog_properties'); - $(this.elements.root).css('z-index', 3002); - $.get(url_for('file_manager.index'), function(data) { - content.append(data); - }); - - var transId = getTransId(self.params); - var t_res; - if (transId.readyState == 4) { - t_res = JSON.parse(transId.responseText); - } - self.trans_id = _.isUndefined(t_res) ? 0 : t_res.data.fileTransId; - - setTimeout(function() { - $(self.$container.find('.file_manager')).on('enter-key', function() { - $($(self.elements.footer).find('.file_manager_ok')).trigger('click'); - }); - }, 200); - if(self.__internal.buttons[1]) - self.__internal.buttons[1].element.disabled = true; - }, - setup: function() { - return { - buttons: [{ - text: gettext('Cancel'), - key: 27, - className: 'btn btn-secondary fa fa-times pg-alertify-button', - },{ - text: gettext('Select'), - key: 13, - className: 'btn btn-primary fa fa-file file_manager_ok pg-alertify-button disabled', - }], - options: { - closableByDimmer: false, - maximizable: false, - closable: false, - movable: true, - padding: !1, - overflow: !1, - model: 0, - resizable: true, - pinnable: false, - modal: false, - autoReset: false, - }, - }; - }, - callback: function(closeEvent) { - var innerbody; - closeEvent.cancel = false; - if (closeEvent.button.text == gettext('Select')) { - var act_variable = document.activeElement.id; - if(act_variable !='refresh_list') { - var newFile = $('.storage_dialog #uploader .input-path').val(), - file_data = { - 'path': $('.currentpath').val(), - }; - - pgAdmin.Browser.Events.trigger('pgadmin-storage:finish_btn:' + this.dialog_type, newFile); - innerbody = $(this.elements.body).find('.storage_content'); - $(innerbody).find('*').off(); - innerbody.remove(); - removeTransId(this.trans_id); - // Ajax call to store the last directory visited once user press select button - - set_last_traversed_dir(file_data, this.trans_id); - } else { - closeEvent.cancel = true; - } - } else if (closeEvent.button.text == gettext('Cancel')) { - innerbody = $(this.elements.body).find('.storage_content'); - $(innerbody).find('*').off(); - innerbody.remove(); - removeTransId(this.trans_id); - pgAdmin.Browser.Events.trigger('pgadmin-storage:cancel_btn:' + this.dialog_type); - } - }, - build: function() { - this.$container = $('
    '); - this.elements.content.appendChild(this.$container.get(0)); - Alertify.pgDialogBuild.apply(this); - }, - hooks: { - onshow: function() {/* This is intentional (SonarQube) */}, - }, - }; -}); diff --git a/web/pgadmin/misc/file_manager/static/js/storage_dialogue.js b/web/pgadmin/misc/file_manager/static/js/storage_dialogue.js deleted file mode 100644 index 38f01f599..000000000 --- a/web/pgadmin/misc/file_manager/static/js/storage_dialogue.js +++ /dev/null @@ -1,45 +0,0 @@ -///////////////////////////////////////////////////////////// -// -// pgAdmin 4 - PostgreSQL Tools -// -// Copyright (C) 2013 - 2022, The pgAdmin Development Team -// This software is released under the PostgreSQL Licence -// -////////////////////////////////////////////////////////////// - -import gettext from 'sources/gettext'; -import Alertify from 'pgadmin.alertifyjs'; - -// Declare the Storage dialog -module.exports = Alertify.dialog('fileStorageDlg', function() { - // Dialog property - return { - settingUpdated: function(key, oldValue, newValue) { - if(key == 'message') { - this.setMessage(newValue); - } - }, - setup: function() { - return { - buttons: [{ - text: gettext('Cancel'), - key: 27, - className: 'btn btn-secondary fa fa-times pg-alertify-button', - }], - options: { - closableByDimmer: false, - maximizable: false, - closable: false, - movable: true, - padding: !1, - overflow: !1, - model: 0, - resizable: true, - pinnable: false, - modal: false, - autoReset: false, - }, - }; - }, - }; -}, true, 'fileSelectionDlg'); diff --git a/web/pgadmin/misc/file_manager/static/js/utility.js b/web/pgadmin/misc/file_manager/static/js/utility.js deleted file mode 100644 index 47bd36f8c..000000000 --- a/web/pgadmin/misc/file_manager/static/js/utility.js +++ /dev/null @@ -1,2008 +0,0 @@ -///////////////////////////////////////////////////////////// -// -// pgAdmin 4 - PostgreSQL Tools -// -// Copyright (C) 2013 - 2022, The pgAdmin Development Team -// This software is released under the PostgreSQL Licence -// -////////////////////////////////////////////////////////////// - -/** - * Filemanager JS core - * - * filemanager.js - * - * @license MIT License - * @author Jason Huck - Core Five Labs - * @author Simon Georget - * @copyright Authors - */ -import Notify from '../../../../static/js/helpers/Notifier'; - -define([ - 'jquery', 'underscore', - 'sources/gettext', 'sources/url_for', 'dropzone', 'sources/pgadmin', - 'sources/csrf', 'tablesorter', 'tablesorter-metric', -], function($, _, gettext, url_for, Dropzone, pgAdmin, csrf) { - - pgAdmin.Browser = pgAdmin.Browser || {}; - - /*--------------------------------------------------------- - Define functions used for various operations - ---------------------------------------------------------*/ - // Set the CSRF Token - csrf.setPGCSRFToken(pgAdmin.csrf_token_header, pgAdmin.csrf_token); - - // Return file extension - var getFileExtension = function(name) { - var found = name.lastIndexOf('.') + 1; - return (found > 0 ? name.substr(found) : ''); - }; - - /* Common function to load: - * en.json language file - * file_manager_config.js config file - * return transaction id - */ - var loadData = function(url) { - return $.ajax({ - async: false, - cache: false, - url: url, - dataType: 'json', - contentType: 'application/json; charset=utf-8', - }); - }; - - var getFileFormat = function(data) { - // Get last selected file format - return $.ajax({ - async: false, - cache: false, - url: url_for('settings.get_file_format_setting'), - data : $.extend({}, data), - dataType: 'json', - contentType: 'application/json; charset=utf-8', - }); - }; - - // Set enable/disable state of list and grid view - var setViewButtonsFor = function(viewMode) { - if (viewMode == 'grid') { - $('.grid').addClass('ON'); - $('.list').removeClass('ON'); - } else { - $('.list').addClass('ON'); - $('.grid').removeClass('ON'); - } - }; - - var save_file_dialog_view = function(view, trans_id) { - return $.ajax({ - url: url_for('file_manager.save_file_dialog_view', { - 'trans_id': trans_id, - }), - type: 'POST', - async: true, - data: JSON.stringify({ - 'view': view, - }), - contentType: 'application/json', - }); - }; - - var save_show_hidden_file_option = function(option, trans_id) { - return $.ajax({ - url: url_for('file_manager.save_show_hidden_file_option', { - 'trans_id': trans_id, - }), - type: 'PUT', - async: true, - data: JSON.stringify({ - 'show_hidden': option, - }), - contentType: 'application/json', - }); - }; - - // nameFormat (), separate filename from extension - var nameFormat = function(input) { - var filename = ''; - if (input.lastIndexOf('.') != -1) { - filename = input.substr(0, input.lastIndexOf('.')); - filename += '.' + input.split('.').pop(); - } else { - filename = input; - } - return filename; - }; - - /* - * Test if Data structure has the 'cap' capability - * 'cap' is one of 'select', 'rename', 'delete', 'download' - */ - var has_capability = function(data, cap) { - if (typeof(data.Capabilities) == 'undefined') { - return true; - } else { - return ($.inArray(cap, data.Capabilities) > -1); - } - }; - - // return filename extension - var getExtension = function(filename) { - if (filename.split('.').length == 1) { - return ''; - } - return filename.split('.').pop(); - }; - - /* - * Binds specific actions to the toolbar based on capability. - * and show/hide buttons - */ - var bindToolbar = function(data) { - - // hide/show rename, upload and create button - if (_.has(data, 'Capabilities')) { - _.each(data.Capabilities, function(cap) { - var target_btn = 'button.' + cap, - $target_el = $('.file_manager').find(target_btn); - if (!has_capability(data, cap) || pgAdmin.FileUtils.hideButtons()) { - $target_el.hide(); - } else { - $target_el.show(); - } - }); - } - - if (!has_capability(data, 'delete') || pgAdmin.FileUtils.hideButtons()) { - $('.file_manager').find('button.delete').hide(); - } else { - $('.file_manager').find('button.delete').on('click',() => { - // hide dimmer - $('.fileinfo .delete_item, .fm_dimmer').show(); - }); - - // take action based on pressed button yes or no - $('.fileinfo .delete_item button.btn_yes').off().on('click', function() { - var path; - if ($('.fileinfo').data('view') == 'grid') { - path = decodeURI($('.fileinfo').find('#contents li.selected .clip span').attr('data-alt')); - if (path.lastIndexOf('/') == path.length - 1) { - data.Path = path; - deleteItem(data); - } else { - deleteItem(data); - } - } else { - path = $('.fileinfo').find('table#contents tbody tr.selected td:first-child').attr('title'); - if (path.lastIndexOf('/') == path.length - 1) { - data.Path = path; - deleteItem(data); - } else { - deleteItem(data); - } - } - // hide dimmer - $('.fileinfo .fm_dimmer').hide(); - }); - - } - - // Download file on download button click - if (!has_capability(data, 'download') || pgAdmin.FileUtils.hideButtons()) { - $('.file_manager').find('button.download').hide(); - } else { - $('.file_manager').find('button.download').off().on('click', function() { - var path, - params = {}; - - params[pgAdmin.csrf_token_header] = pgAdmin.csrf_token; - - if ($('.fileinfo').data('view') == 'grid') { - path = $('.fileinfo li.selected').find('.clip span').attr('data-alt'); - } else { - path = $('.fileinfo').find('table#contents tbody tr.selected td:first-child').attr('title'); - } - download_file(path); - }); - } - }; - - // enable/disable button when files/folder are loaded - var enable_disable_btn = function() { - if ($('.fileinfo').data('view') == 'grid') { - var $grid_file = $('.file_manager').find('#contents li.selected'); - $grid_file.removeClass('selected'); - $('.file_manager').find('button.delete').prop('disabled', true); - $('.file_manager').find('button.download').prop('disabled', true); - $('.file_manager').find('button.rename').prop('disabled', true); - if ($grid_file.length > 0) { - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - } - } else { - var $list_file = $('.fileinfo').find('table#contents tbody tr.selected'); - $list_file.removeClass('selected'); - $('.file_manager').find('button.delete').prop('disabled', true); - $('.file_manager').find('button.download').prop('disabled', true); - $('.file_manager').find('button.rename').prop('disabled', true); - if ($list_file.length > 0) { - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - } - } - - $('.delete_item').hide(); - // clear address bar - $('.file_manager #uploader .input-path').show(); - $('.file_manager #uploader .show_selected_file').remove(); - }; - - /* - * Rename the current item and returns the new name. - * by double clicking or by clicking the "Rename" button in - * table(list) views. - */ - var renameItem = function(data) { - var finalName = '', - lg = pgAdmin.FileUtils.lg, - getNewName = function(rname) { - if (rname !== '') { - var givenName = nameFormat(rname), - suffix = getExtension(data.Filename); - if (suffix.length > 0) { - givenName = givenName + '.' + suffix; - } - - var oldPath = data.Path, - post_data = { - 'mode': 'rename', - 'old': data.Path, - 'new': givenName, - }; - - $.ajax({ - type: 'POST', - data: JSON.stringify(post_data), - url: pgAdmin.FileUtils.fileConnector, - dataType: 'json', - contentType: 'application/json; charset=utf-8', - async: false, - }) - .done(function(resp) { - var result = resp.data.result; - if (result.Code === 1) { - var newPath = result['New Path'], - newName = result['New Name'], - title = $('#preview h1').attr('title'); - - if (typeof title != 'undefined' && title == oldPath) { - $('#preview h1').text(newName); - } - - if ($('.fileinfo').data('view') == 'grid') { - $('.fileinfo span[data-alt="' + oldPath + '"]').parent().next('div span').text(newName); - $('.fileinfo span[data-alt="' + oldPath + '"]').attr('data-alt', newPath); - } else { - $('.fileinfo td[title="' + oldPath + '"]').text(newName); - $('.fileinfo td[title="' + oldPath + '"]').attr('title', newPath); - } - $('#preview h1').html(newName); - - // actualized data for binding - data.Path = newPath; - data.Filename = newName; - - // UnBind toolbar functions. - $('.fileinfo').find('button.rename, button.delete, button.download').off(); - - Notify.success(lg.successful_rename); - } else { - Notify.error(result.Error); - } - - finalName = result['New Name']; - }); - } - }; - - getNewName(data.NewFilename); - return finalName; - }; - - /* - * delete the folder or files by clicking the "Delete" button - * in table(list) view - */ - var deleteItem = function(data) { - var isDeleted = false, - lg = pgAdmin.FileUtils.lg; - - var doDelete = function(sel_data) { - var post_data = { - 'mode': 'delete', - 'path': sel_data.Path, - }; - - $.ajax({ - type: 'POST', - data: JSON.stringify(post_data), - url: pgAdmin.FileUtils.fileConnector, - dataType: 'json', - contentType: 'application/json; charset=utf-8', - async: false, - }) - .done(function(resp) { - var result = resp.data.result; - if (result.Code === 1) { - isDeleted = true; - if (isDeleted) { - Notify.success(lg.successful_delete); - var rootpath = result.Path.substring(0, result.Path.length - 1); // removing the last slash - rootpath = rootpath.substr(0, rootpath.lastIndexOf('/') + 1); - getFolderInfo(rootpath); - } - } else { - isDeleted = false; - Notify.error(result.Error); - } - }); - return isDeleted; - }; - - doDelete(data); - return isDeleted; - }; - - /*--------------------------------------------------------- - Functions to Retrieve File and Folder Details - ---------------------------------------------------------*/ - /* - * Retrieves information about the specified file as a JSON - * object and uses that data to populate a template for - * list views. Binds the toolbar for that file/folder to - * enable specific actions. Called whenever an item is - * clicked in list views. - */ - var getFileInfo = function(file) { - // Update location for status, upload, & new folder functions. - pgAdmin.FileUtils.setUploader(file); - var capabilities = pgAdmin.FileUtils.data.capabilities, - is_file_valid = false, - post_data = { - 'path': file, - 'mode': 'getinfo', - }; - - // Retrieve the data & populate the template. - $.ajax({ - type: 'POST', - data: JSON.stringify(post_data), - url: pgAdmin.FileUtils.fileConnector, - dataType: 'json', - contentType: 'application/json; charset=utf-8', - async: false, - }) - .done(function(resp) { - var data = resp.data.result; - if (data.Code === 1) { - $('.file_manager_ok').removeClass('disabled'); - $('.file_manager_ok').attr('disabled', false); - data.Capabilities = capabilities; - bindToolbar(data); - if (data.FileType == 'Directory') { - // Enable/Disable level up button - enab_dis_level_up(); - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - $('.file_manager button.delete, .file_manager button.rename').attr('disabled', 'disabled'); - $('.file_manager button.download').attr('disabled', 'disabled'); - - if (file.charAt(file.length - 1) != '/' && file.charAt(file.length - 1) != '\\') { - file += '/'; - } - getFolderInfo(file); - } else { - is_file_valid = true; - } - } else { - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - Notify.error(data.Error); - } - - // Disable select button if user select file. - if (pgAdmin.FileUtils.data.Capabilities.includes('select_folder')) { - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - } - - }); - return is_file_valid; - }; - - var checkPermission = function(path) { - var permission = false, - post_data = { - 'path': path, - 'mode': 'permission', - }; - - $.ajax({ - type: 'POST', - data: JSON.stringify(post_data), - url: pgAdmin.FileUtils.fileConnector, - dataType: 'json', - contentType: 'application/json; charset=utf-8', - async: false, - }) - .done(function(resp) { - var data = resp.data.result; - if (data.Code === 1) { - permission = true; - } else { - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - Notify.error(data.Error); - } - }) - .fail(function() { - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - Notify.error( - gettext('Error occurred while checking access permission.') - ); - }); - return permission; - }; - - var getNoDataView = function(data) { - var lg = pgAdmin.FileUtils.lg; - var cap_no_folders = ['upload', 'create']; - data.Capabilities = cap_no_folders; - bindToolbar(data); - - return `
    ${lg.could_not_retrieve_folder}
    `; - }; - - var getCapClasses = function(item_data, capabilities) { - let capClasses = ''; - capClasses = Object.keys(capabilities).map(function(cap) { - if (has_capability(item_data, capabilities[cap])) { - return 'cap_' + capabilities[cap]; - } - }).join(' '); - return capClasses; - }; - - var getGridView = function(data, capabilities) { - let ret_ele = '
      ', - no_data = _.isEmpty(data); - - if(!no_data) { - ret_ele += Object.keys(data).sort(function keyOrder(x, y) { - return pgAdmin.natural_sort(x.toLowerCase(), y.toLowerCase()); - }).map(function(key) { - let item_data = data[key], - props = item_data.Properties, - filename = _.escape(item_data.Filename), - icon_type = '', - cap_classes = ''; - - cap_classes = getCapClasses(item_data, capabilities); - - item_data.Capabilities = capabilities; - bindToolbar(item_data); - - if (item_data.file_type == 'dir') { - icon_type = 'fa fa-folder-open fm_folder_grid'; - props.Size = ''; - } else if (item_data.file_type == 'drive') { - icon_type = 'fa fa-hdd fm_drive'; - props.Size = ''; - } else { - icon_type = 'fa fa-file-alt fm_file_grid'; - } - - /* For the html ele */ - let item_ele = - `
    • -
      - `; - - if (item_data.Protected == 1) { - item_ele += ''; - } - - item_ele += '
      '; - - if (!has_capability(item_data, 'rename')) { - item_ele += `${filename}`; - } else { - item_ele += - `
      - - ${filename} -
      `; - } - if (props.Width && props.Width != '') { - item_ele += `${props.Width}x${props.Height}`; - } - if (props.Size && props.Size != '') { - item_ele += `${props.Size}`; - } - if (props['Date Created'] && props['Date Created'] != '') { - item_ele += `${props['Date Created']}`; - } - if (props['Date Modified'] && props['Date Modified'] != '') { - item_ele += `${props['Date Modified']}`; - } - item_ele += '
    • '; - - return item_ele; - }).join('\n'); - } - - ret_ele += '
    '; - - if(no_data) { - ret_ele += getNoDataView(data); - } - return ret_ele; - }; - - var getListView = function(data, capabilities) { - let lg = pgAdmin.FileUtils.lg; - let no_data = _.isEmpty(data); - - /* file_listing_table class makes height 100%, because of which No folder message is not displayed - * file_listing_table_no_data will be removed when new folder is created - */ - let ret_ele = - ` - - - - - - - - `; - - if(!no_data) { - ret_ele += Object.keys(data).sort(function keyOrder(x, y) { - return pgAdmin.natural_sort(x.toLowerCase(), y.toLowerCase()); - }).map(function(key) { - let item_data = data[key], - props = item_data.Properties, - icon_type = '', - class_type = '', - cap_classes = ''; - - cap_classes = getCapClasses(item_data, capabilities); - - item_data.Capabilities = capabilities; - bindToolbar(item_data); - - if (item_data.file_type == 'dir') { - class_type = 'tbl_folder'; - icon_type = 'fa fa-folder-open fm_folder_list'; - props.Size = ''; - } else if (item_data.file_type == 'drive') { - class_type = 'tbl_drive'; - icon_type = 'fa fa-hdd'; - props.Size = ''; - } else { - class_type = 'tbl_file'; - icon_type = 'fa fa-file-alt'; - } - - /* For the html ele */ - let item_ele = - ` - '; - if (props.Size && props.Size != '') { - item_ele += ``; - } else { - item_ele += ''; - } - - if (props['Date Modified'] && props['Date Modified'] != '') { - item_ele += ``; - } else { - item_ele += ''; - } - - item_ele += ''; - - return item_ele; - }).join('\n'); - } - - ret_ele += - ` -
    - ${lg.name} - - ${lg.size} - - ${lg.modified} -
    `; - - let data_protected = ''; - if (item_data.Protected == 1) { - data_protected = ''; - } - if (!has_capability(data[key], 'rename')) { - item_ele += - `${data_protected}; - ${_.escape(item_data.Filename)}`; - } else { - item_ele += - `
    - -
    -
    - - ${data_protected} - ${_.escape(item_data.Filename)} -
    -
    -
    `; - } - item_ele += '
    ${props.Size}${props['Date Modified']}
    `; - - if(no_data) { - ret_ele += getNoDataView(data); - } - return ret_ele; - }; - - var enableSelect = function() { - // Enable select button if user select folder. - if (pgAdmin.FileUtils.data && pgAdmin.FileUtils.data.Capabilities.includes('select_folder')) { - $('.file_manager_ok').removeClass('disabled'); - $('.file_manager_ok').attr('disabled', false); - } - }; - - var disableSelect = function() { - // Disable select button if user select file. - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - }; - - /* - * Retrieves data for all items within the given folder and - * creates a list view. - */ - var getFolderInfo = function(path, file_type, user_input) { - $('.storage_dialog #uploader .input-path').prop('disabled', true); - if (!file_type) { - file_type = ''; - } - var capabilities = pgAdmin.FileUtils.data.Capabilities; - enableSelect(); - - // Update location for status, upload, & new folder functions. - pgAdmin.FileUtils.setUploader(path); - if(user_input) { - $('.storage_dialog #uploader .input-path').val(path+user_input); - } - - // set default selected file type - if (file_type === '') { - file_type = $('.change_file_types select').val(); - } - - // navigate to directory or path when clicked on breadcrumbs - $('.file_manager a.breadcrumbs').off().on('click', function() { - var curr_path = $(this).attr('data-path'), - current_dir = $(this).html(), - move_to = curr_path.substring( - 0, curr_path.lastIndexOf(current_dir) - ) + current_dir; - - getFolderInfo(move_to); - enab_dis_level_up(); - }); - - // hide select file if we are listing drives in windows. - if (pgAdmin.FileUtils.hideButtons()) { - $('.allowed_file_types .change_file_types').hide(); - } else { - $('.allowed_file_types .change_file_types').show(); - } - - var loading_icon_url = url_for( - 'static', { - 'filename': 'img/loading.gif', - } - ); - - // Display an activity indicator. - $('.fileinfo').find('span.activity').html( - '' + gettext('Loading...') + '/>'
-    );
-
-    var post_data = {
-      'path': path,
-      'mode': 'getfolder',
-      'file_type': file_type || '*',
-      'show_hidden': $('#show_hidden').prop('checked'),
-    };
-
-    $.ajax({
-      type: 'POST',
-      data: JSON.stringify(post_data),
-      url: pgAdmin.FileUtils.fileConnector,
-      dataType: 'json',
-      contentType: 'application/json; charset=utf-8',
-      async: false,
-    })
-      .done(function(resp) {
-        $('.storage_dialog #uploader .input-path').prop('disabled', false);
-        var result = '',
-          data = resp.data.result;
-        let isGridView = false;
-        // hide activity indicator
-        $('.fileinfo').find('span.activity').hide();
-        if (data.Code === 0) {
-          Notify.error(data.Error);
-          return;
-        }
-
-        var $this, orig_value, newvalue;
-
-        // generate HTML for files/folder and render into container
-        if ($('.fileinfo').data('view') == 'grid') {
-          result += getGridView(data, capabilities);
-          isGridView = true;
-        } else {
-          result += getListView(data, capabilities);
-        }
-
-        // Add the new markup to the DOM.
-        $('.fileinfo .file_listing').html(result);
-
-        let $listing_table = $('.fileinfo .file_listing .file_listing_table');
-
-        $listing_table.tablesorter({
-          widgets: [ 'resizable', 'stickyHeaders' ],
-          widgetOptions : {
-            stickyHeaders_attachTo:'.file_listing',
-            stickyHeaders_offset: 0,
-            resizable_widths: ['400px', '100px', '175px'],
-          },
-        });
-
-        /* In order to fit our UI, some things need to be explicitly set
-         * as tablesorter resizable is creating trouble.
-         */
-        $listing_table.on( 'resizableComplete', function() {
-          let wo = this.config.widgetOptions;
-          $.tablesorter.resizable.setWidth($listing_table.find('th[data-column= 0) - $(this).click(); - // If folder then first select and then double click to open folder/drive - else if ($(this).find('.fa-folder-open').length || $(this).find('.fa-hdd').length) { - $(this).click(); - setTimeout(() => { $(self).trigger('dblclick'); }, 10); - } - }; - - $listing_table.on( 'tablesorter-ready', function() { - let wo = this.config.widgetOptions; - if($.tablesorter.storage($listing_table[0], 'tablesorter-table-resized-width') === '') { - $.tablesorter.resizable.setWidth($listing_table, $('.fileinfo .file_listing').width()); - } - $.tablesorter.resizable.setWidth($listing_table.find('th[data-column="2"]'), wo.resizable_widths[2]); - $listing_table.trigger('resizableUpdate'); - - // Table Sorter writes table elements randomly so we need to handle some corner cases manually - $('#show_hidden').off('keydown').on('keydown', function(event) { - if (!isGridView && event.keyCode == 9 && event.shiftKey) { - event.preventDefault(); - $listing_table.find('tbody tr:last').trigger('focus'); - } - }); - - $listing_table.find('tbody tr').off('keydown').on('keydown', function(event) { - // If key is pressed then we need to trigger click so that it can select file - if (event.keyCode == 13 || event.keyCode == 32) { - clickOnFileFolderManually.call(this, event); - } else if (event.keyCode == 9) { - if (event.shiftKey) { - // When first tr losses focus and shift + tab > we need to set focus on header - if ($(this).prev().length == 0) { - event.preventDefault(); - $listing_table.find('th.tablesorter-header:last').trigger('focus'); - } - } else { - // When last tr losses focus and Tab was pressed > we need to set focus on checkbox - if ($(this).next().length == 0) { - event.preventDefault(); - $('#show_hidden').trigger('focus'); - } - } - } - }); - - $listing_table.find('th.tablesorter-header').off('keydown').on('keydown', function(event) { - // If key is pressed then we need to trigger click so that it can sort - if (event.keyCode == 13 || event.keyCode == 32) { - event.preventDefault(); - event.stopPropagation(); - $(this).trigger('click'); - } - }); - }); - - if(isGridView) { - $('.file_manager').find('#contents li').off('keydown').on('keydown', function(event) { - // If key is pressed then we need to trigger click so that it can sort - if (event.keyCode == 13 || event.keyCode == 32) { - clickOnFileFolderManually.call(this, event); - } - }); - } - - // rename file/folder - $('.file_manager button.rename').off().on('click', function(e) { - - if ($('.fileinfo').data('view') == 'grid') { - e.stopPropagation(); - $this = $('.file_manager').find('#contents li.selected div'); - orig_value = decodeURI($this.find('span.less_text').attr('title')); - newvalue = orig_value.substring(0, orig_value.indexOf('.')); - - if (newvalue === '') { - newvalue = decodeURI(orig_value); - } - - $this.find('input').toggle().val(newvalue).trigger('focus'); - $this.find('span').toggle(); - - // Rename folder/file on pressing enter key - $('.file_manager').off().on('keyup', function(event) { - if (event.keyCode == 13) { - event.stopPropagation(); - $('.fileinfo #contents li.selected div').find( - 'input' - ).trigger('blur'); - } - }); - } else if ($('.fileinfo').data('view') == 'list') { - e.stopPropagation(); - $this = $('.fileinfo').find( - 'table#contents tbody tr.selected td.tbl_file' - ); - if($this.length == 0) { - $this = $('.fileinfo').find( - 'table#contents tbody tr.selected td.tbl_folder' - ); - // putting temporary class to distiguish between folder rename & double click. - $this.addClass('tbl_folder_rename'); - } - orig_value = decodeURI($this.find('span.less_text').html()); - newvalue = orig_value.substring(0, orig_value.lastIndexOf('.')); - - if (orig_value.lastIndexOf('/') == orig_value.length - 1 || (_.isEmpty(newvalue) || _.isUndefined(newvalue) || _.isNull(newvalue))) { - newvalue = decodeURI(orig_value); - } - - $this.find('.fm_file_rename').toggle().val(newvalue).trigger('focus'); - $this.find('.fm_file_name').toggle(); - - // Rename folder/file on pressing enter key - $('.file_manager').off().on('keyup', function(event) { - if (event.keyCode == 13) { - event.stopPropagation(); - $this.find('fm_file_rename').trigger('blur'); - } - }); - } - }); - - // Rename UI handling - $('.fileinfo #contents li div').on('blur dblclick', 'input', function(e) { - e.stopPropagation(); - - var old_name = decodeURI($(this).siblings('div').find('.less_text').attr('title')); - newvalue = old_name.substring(0, old_name.indexOf('.')); - var last = getFileExtension(old_name), - file_data, new_name, file_path, full_name; - - if (old_name.indexOf('.') == 0) { - last = ''; - } - - if (newvalue == '') { - newvalue = decodeURI(old_name); - } - - if (e.type == 'keydown') { - if (e.which == 13) { - full_name = decodeURI($(this).val()) + ( - last !== '' ? '.' + last : '' - ); - - $(this).toggle(); - $(this).siblings('span').toggle().html(full_name); - - new_name = decodeURI($(this).val()); - file_path = decodeURI($(this).parent().parent().find( - 'span' - ).attr('data-alt')); - file_data = { - 'Filename': old_name, - 'Path': file_path, - 'NewFilename': new_name, - }; - - if (newvalue !== new_name) { - renameItem(file_data); - var parent = $('.currentpath').val(); - getFolderInfo(parent); - } - e.stopPropagation(); - } - - if ( - e.which == 38 || e.which == 40 || e.which == 37 || - e.which == 39 || e.keyCode == 32 - ) { - e.stopPropagation(); - } - } else if (e.type == 'focusout') { - if ($(this).css('display') == 'inline-block' || $(this).css('display') == 'inline') { - full_name = decodeURI( - $(this).val() - ) + (last !== '' ? '.' + last : ''); - - if (newvalue !== new_name) { - - $(this).toggle(); - $(this).siblings('span').toggle().html(full_name); - - //check if user is trying to rename folder - let isFolder = $(this).closest('.tbl_folder').length > 0; - - new_name = decodeURI($(this).val()); - file_path = decodeURI($(this).parent().parent().find( - 'span' - ).attr('data-alt')); - file_data = { - 'Filename': old_name, - 'Path': file_path, - 'NewFilename': new_name, - 'isFolder': isFolder, - }; - - renameItem(file_data); - let current_path = $('.currentpath').val(); - if(isFolder == true) { - // if its folder rename, remove the temporary added class - $(this).closest('.tbl_folder').removeClass('tbl_folder_rename'); - if(current_path.includes('\\')) { - current_path = $('.currentpath').val().split('\\').slice(0, -2).join('\\')+'\\'; - } - else { - current_path = $('.currentpath').val().split('/').slice(0, -2).join('/')+'/'; - } - } - getFolderInfo(current_path); - } - } - } else { - e.stopPropagation(); - } - }); - - $('.fileinfo table#contents tr td div').on( - 'blur dblclick', 'input', - function(e) { - var old_name = decodeURI($(this).siblings('div').find('.less_text').attr('title')), - new_value = old_name.substring(0, old_name.indexOf('.')), - last = getFileExtension(old_name); - if (old_name.indexOf('.') == 0) { - last = ''; - } - - if (new_value == '') { - new_value = old_name; - } - - if (e.type == 'focusout') { - if ($(this).css('display') == 'inline-block' || $(this).css('display') == 'inline') { - var full_name = decodeURI($(this).val()) + ( - last !== '' ? '.' + last : '' - ); - - if (new_value !== new_name) { - - $(this).toggle(); - $(this).siblings('span').toggle().html(full_name); - - let isFolder = $(this).closest('.tbl_folder').length > 0; - - var new_name = decodeURI($(this).val()), - file_path = decodeURI($(this).parent().parent().attr('title')), - file_data = { - 'Filename': old_name, - 'Path': file_path, - 'NewFilename': new_name, - 'isFolder': isFolder, - }; - - renameItem(file_data); - let current_path = $('.currentpath').val(); - if(isFolder == true) { - // if its folder rename, remove the temporary added class - $(this).closest('.tbl_folder').removeClass('tbl_folder_rename'); - if(current_path.includes('\\')) { - current_path = $('.currentpath').val().split('\\').slice(0, -2).join('\\')+'\\'; - } - else { - current_path = $('.currentpath').val().split('/').slice(0, -2).join('/')+'/'; - } - } - getFolderInfo(current_path); - } - } - } else { - e.stopPropagation(); - } - }); - - var data_cap = {}; - data_cap.Capabilities = capabilities; - /* - * Bind click events - * Select items - afolder dblclick - */ - if ($('.fileinfo').data('view') == 'grid') { - // Get into folder on dblclick - $('.fileinfo').find('#contents li').dblclick(function(e) { - e.stopPropagation(); - // Enable/Disable level up button - enab_dis_level_up(); - - var file_path = decodeURI($(this).find('span').attr('data-alt')); - - if (file_path.lastIndexOf('/') == file_path.length - 1 || file_path.lastIndexOf('\\') == file_path.length - 1) { - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - $('.file_manager button.delete, .file_manager button.rename').attr('disabled', 'disabled'); - $('.file_manager button.download').attr('disabled', 'disabled'); - - getFolderInfo(file_path); - - } else { - var is_valid_file = getFileInfo(file_path); - if (is_valid_file && check_file_capability(e, data_cap, 'grid')) { - $('.file_manager_ok').trigger('click'); - } - } - }); - - $('.fileinfo').find('#contents li').on('click', function(e) { - e.stopPropagation(); - var file_path = decodeURI($(this).find('.clip span').attr('data-alt')), - is_protected = $(this).find( - '.clip span.fm_lock_icon' - ).attr('data-protected'); - - if (file_path.lastIndexOf('/') == file_path.length - 1 || file_path.lastIndexOf('\\') == file_path.length - 1) { - if ( - has_capability(data_cap, 'select_folder') && - is_protected == undefined - ) { - $(this).parent().find('li.selected').removeClass('selected'); - $(this).addClass('selected'); - - $('.file_manager_ok').removeClass('disabled'); - $('.file_manager_ok').attr('disabled', false); - $('.file_manager button.delete, .file_manager button.rename').removeAttr( - 'disabled', 'disabled' - ); - $('.file_manager button.download').attr( - 'disabled', 'disabled' - ); - // set selected folder name in breadcrums - $('.file_manager #uploader .input-path').hide(); - $('.file_manager #uploader .show_selected_file').remove(); - $('' + file_path + '').appendTo( - '.file_manager #uploader .filemanager-path-group' - ); - } - pgAdmin.FileUtils.setUploader(file_path); - } else { - if ( - has_capability(data_cap, 'select_file') && - is_protected == undefined - ) { - $(this).parent().find('li.selected').removeClass('selected'); - $(this).addClass('selected'); - $('.file_manager_ok').removeClass('disabled'); - $('.file_manager_ok').attr('disabled', false); - $('.file_manager button.delete, .file_manager button.download, .file_manager button.rename').removeAttr( - 'disabled' - ); - // set selected folder name in breadcrums - $('.file_manager #uploader .show_selected_file').remove(); - } - - getFileInfo(file_path); - } - }); - } else { - $('.fileinfo table#contents tbody tr').on('click', function(e) { - e.stopPropagation(); - var file_path = decodeURI($('td:first-child', this).attr('title')), - is_protected = $('td:first-child', this).find( - 'i.tbl_lock_icon' - ).attr('data-protected'); - - if (file_path.lastIndexOf('/') == file_path.length - 1 || file_path.lastIndexOf('\\') == file_path.length - 1) { - if (has_capability(data_cap, 'select_folder') && is_protected == undefined) { - $(this).parent().find('tr.selected').removeClass('selected'); - $('td:first-child', this).parent().addClass('selected'); - $('.file_manager_ok').removeClass('disabled'); - $('.file_manager_ok').attr('disabled', false); - $('.file_manager button.download').attr('disabled', 'disabled'); - $('.file_manager button.delete, .file_manager button.rename').removeAttr('disabled'); - - // set selected folder name in breadcrums - $('.file_manager #uploader .input-path').hide(); - $('.file_manager #uploader .show_selected_file').remove(); - $('' + file_path + '').appendTo( - '.file_manager #uploader .filemanager-path-group' - ); - } - pgAdmin.FileUtils.setUploader(file_path); - } else { - if (has_capability(data_cap, 'select_file') && is_protected == undefined) { - $(this).parent().find('tr.selected').removeClass('selected'); - $('td:first-child', this).parent().addClass('selected'); - $('.file_manager button.delete, .file_manager button.download, .file_manager button.rename').removeAttr( - 'disabled' - ); - // set selected folder name in breadcrums - $('.file_manager #uploader .show_selected_file').remove(); - } - - getFileInfo(file_path); - } - }); - - $('.fileinfo table#contents tbody tr').on('dblclick', function(e) { - e.stopPropagation(); - // Enable/Disable level up button - enab_dis_level_up(); - var file_path = $('td:first-child', this).attr('title'); - - if (file_path.lastIndexOf('/') == file_path.length - 1 || file_path.lastIndexOf('\\') == file_path.length - 1) { - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - $('.file_manager button.download').attr('disabled', 'disabled'); - $('.file_manager button.delete, .file_manager button.rename').attr('disabled', 'disabled'); - getFolderInfo(file_path); - } else { - var is_valid_file = getFileInfo(file_path); - if ( - is_valid_file && check_file_capability(e, data_cap, 'table') - ) { - $('.file_manager_ok').trigger('click'); - } - } - }); - - } - }) - .fail(function() { - $('.storage_dialog #uploader .input-path').prop('disabled', false); - }); - }; - var homedir='/'; - // Enable/Disable level up button - var enab_dis_level_up = function() { - $('.file_manager #uploader .input-path').show(); - $('.show_selected_file').remove(); - - setTimeout(function() { - var b = $('.currentpath').val(), - $level_up = $('.file_manager').find('button.level-up'), - $home_btn = $('.file_manager').find('button.home'); - - (b === '/') ? $level_up.attr('disabled', 'disabled') : $level_up.removeAttr('disabled'); - (b === homedir) ? $home_btn.attr('disabled', 'disabled') : $home_btn.removeAttr('disabled'); - - }, 100); - }; - - // Check if user can Select file - var check_file_capability = function(event, data_cap, view_type) { - var current_element = event.currentTarget, - is_protected; - - if (view_type == 'grid') { - is_protected = $(current_element).find( - '.clip span.fm_lock_icon' - ).attr('data-protected'); - } else { - is_protected = $(current_element).find('td:first-child').find( - 'i.tbl_lock_icon' - ).attr('data-protected'); - } - - return has_capability(data_cap, 'select_file') && - is_protected == undefined; - }; - - // Download selected file - var download_file = function (path) { - - var data = { 'path': path, 'mode': 'download' }, - params = {}; - - params[pgAdmin.csrf_token_header] = pgAdmin.csrf_token; - - $.ajax({ - type: 'POST', - url: pgAdmin.FileUtils.fileConnector, - contentType: false, - headers: params, - xhrFields: { - responseType: 'blob', - }, - cache: false, - data: JSON.stringify(data), - success: function (blob, status, xhr) { - // check for a filename - var filename = xhr.getResponseHeader('filename'); - - if (typeof window.navigator.msSaveBlob !== 'undefined') { - // IE workaround for "HTML7007: One or more blob URLs were revoked by closing the blob for which they were created. These URLs will no longer resolve as the data backing the URL has been freed." - window.navigator.msSaveBlob(blob, filename); - } else { - var URL = window.URL || window.webkitURL; - var downloadUrl = URL.createObjectURL(blob); - - if (filename) { - // use HTML5 a[download] attribute to specify filename - var a = document.createElement('a'); - // safari doesn't support this yet - if (typeof a.download === 'undefined') { - window.location.href = downloadUrl; - } else { - a.href = downloadUrl; - a.download = filename; - document.body.appendChild(a); - a.click(); - } - } else { - window.location.href = downloadUrl; - } - - setTimeout(function () { URL.revokeObjectURL(downloadUrl); }, 100); // cleanup - } - }, - error: function (error) { - Notify.error(error); - }, - }); - }; - - /*--------------------------------------------------------- - Initialization - Entry point - ---------------------------------------------------------*/ - /* - * get transaction id to generate request url and - * to generate config files on runtime - */ - pgAdmin.FileUtils = { - init: function() { - var fm_url = url_for('file_manager.get_trans_id'), - transId = loadData(fm_url), - t_res, - t_id; - - if (transId.readyState == 4) { - t_res = JSON.parse(transId.responseText); - } - t_id = _.isUndefined(t_res) ? 0 : t_res.data.fileTransId; - var root_url = url_for('file_manager.index'), - file_manager_config_json = root_url + t_id + '/file_manager_config.json', - fileConnector = root_url + 'filemanager/' + t_id + '/', - cfg = loadData(file_manager_config_json), - config; - - this.fileConnector = fileConnector; - this.transId = t_id; - // load user configuration file - if (cfg.readyState == 4) { - this.config = config = JSON.parse(cfg.responseText); - homedir=config.options.homedir; - } - - if (_.isUndefined(config)) - return; - - // set main url to filemanager and its capabilites - var fileRoot = config.options.fileRoot, - capabilities = config.options.capabilities; - - /* - * Get localized messages from file - * through culture var or from URL - */ - - var lg = [], - enjson = url_for('file_manager.index') + 'en.json', - lgf = loadData(enjson); - - if (lgf.readyState == 4) { - this.lg = lg = JSON.parse(lgf.responseText); - } - - // create and enable user to create new file - if ( - config.options.dialog_type == 'select_file' || - config.options.dialog_type == 'create_file' || - config.options.dialog_type == 'storage_dialog' - ) { - // Create file selection dropdown - var allowed_types = config.options.allowed_file_types, - types_len = allowed_types.length, - select_box = ''; - - if (types_len > 0) { - var i = 0, - t, - have_all_types = false; - - let fileFormats = ''; - let response = getFileFormat(config.options.allowed_file_types); - let lastSelectedFormat = response.responseJSON.info; - - while (i < types_len) { - t = allowed_types[i]; - if ((types_len == 1 || t != '*')) { - if(t === lastSelectedFormat) - fileFormats += ''; - else - fileFormats += ''; - have_all_types = (have_all_types || (t == '*')); - } else if ((lastSelectedFormat === '*')) { - fileFormats += ''; - have_all_types = (have_all_types || (t == '*')); - } - i++; - } - - if (!have_all_types) { - fileFormats += ''; - } - - select_box = `
    -
    ` + - gettext('Show hidden files and folders?') + - ` -
    -
    - - -
    `; - } - - $('.allowed_file_types').html(select_box); - - $('.allowed_file_types select').on('change', function() { - var selected_val = $(this).val(), - curr_path = $('.currentpath').val(), - user_input_file = null, - input_path = $('.storage_dialog #uploader .input-path').val(); - config.options.selectedFormat = selected_val; - $.ajax({ - url: url_for('settings.save_file_format_setting'), - type: 'POST', - contentType: 'application/json', - data: JSON.stringify(config.options), - }); - if (curr_path.endsWith('/')) { - user_input_file = input_path.substring(curr_path.lastIndexOf('/')+1); - } else { - user_input_file = input_path.substring(curr_path.lastIndexOf('\\')+1); - } - getFolderInfo(curr_path, selected_val, user_input_file); - }); - - // If user have preference to show hidden files - if (config.options.show_hidden_files) { - setTimeout(function() { - $('#show_hidden').trigger('click'); - }, 10); - } - // handle show hidden files functionality - this.handleClick = function(cb) { - var tmp_data = { - 'is_checked': false, - }; - - if (cb.checked) { - $('div.allowed_file_types select').trigger('change'); - tmp_data['is_checked'] = true; - } else { - // User wants to hide it again - $('div.allowed_file_types select').trigger('change'); - tmp_data['is_checked'] = false; - } - // Save it in preference - save_show_hidden_file_option(tmp_data['is_checked'], pgAdmin.FileUtils.transId); - }; - } - - /*--------------------------------------------------------- - Item Actions - Object events - ---------------------------------------------------------*/ - - $('.file_manager').attr('data-platform', config.options.platform_type); - - // Switch to folder view - $('.file_manager .fileinfo').on('click', function() { - enable_disable_btn(); - }); - - - - // Refresh current directory - $('.file_manager .refresh').on('click', function() { - enable_disable_btn(); - - var curr_path = $('.currentpath').val(), - path; - - $('.file_manager #uploader .input-path').val(curr_path); - if (curr_path.endsWith('/')) { - path = curr_path.substring(0, curr_path.lastIndexOf('/')) + '/'; - } else { - path = curr_path.substring(0, curr_path.lastIndexOf('\\')) + '\\'; - } - getFolderInfo(path); - }); - - // hide message prompt and dimmer if clicked no - $('.delete_item button.btn_no').on('click', function() { - $('.delete_item, .fileinfo .fm_dimmer').hide(); - }); - - // Disable button on load - $('.file_manager').find('button.rename').attr('disabled', 'disabled'); - - // stop click event on dimmer click - $('.fileinfo .fm_dimmer').on('click', function(e) { - e.stopPropagation(); - }); - - $('.fileinfo .replace_file').not( - $(this).find('span.pull-right') - ).on( - 'click', - function(e) { - $('#uploader .filemanager-btn-group').off().on( - 'click', - function() { - $('.fileinfo .delete_item, .fileinfo .replace_file, .fileinfo .fm_dimmer').hide(); - }); - e.stopPropagation(); - }); - - // Set initial view state. - $('.fileinfo').data('view', config.options.defaultViewMode); - setViewButtonsFor(config.options.defaultViewMode); - - // Upload click event - $('.file_manager .uploader').on('click', 'a', function(e) { - e.preventDefault(); - var b = $('.currentpath').val(), - node_val = $(this).next().text(), - parent = b.substring(0, b.slice(0, -1).lastIndexOf(node_val)); - getFolderInfo(parent); - }); - - // re-render the home view - $('.file_manager .home').on('click', function() { - var currentViewMode = $('.fileinfo').data('view'); - $('.fileinfo').data('view', currentViewMode); - getFolderInfo(homedir); - enab_dis_level_up(); - }); - - // Go one directory back - $('.file_manager .level-up').on('click', function() { - var b = $('.currentpath').val(); - // Enable/Disable level up button - enab_dis_level_up(); - - if (b.endsWith('\\') || b.endsWith('/')) { - b = b.substring(0, b.length - 1); - } - - if (b != '/') { - var parent; - if (b.lastIndexOf('/') > b.lastIndexOf('\\')) { - parent = b.substring(0, b.slice(0, -1).lastIndexOf('/')) + '/'; - } else { - parent = b.substring(0, b.slice(0, -1).lastIndexOf('\\')) + '\\'; - } - - var d = $('.fileinfo').data('view'); - $('.fileinfo').data('view', d); - getFolderInfo(parent); - } - }); - - // set buttons to switch between grid and list views. - $('.file_manager .grid').on('click',() => { - setViewButtonsFor('grid'); - $('.fileinfo').data('view', 'grid'); - enable_disable_btn(); - getFolderInfo($('.currentpath').val()); - save_file_dialog_view('grid', pgAdmin.FileUtils.transId); - }); - - // Show list mode - $('.file_manager .list').on('click',() => { - setViewButtonsFor('list'); - $('.fileinfo').data('view', 'list'); - enable_disable_btn(); - getFolderInfo($('.currentpath').val()); - save_file_dialog_view('list', pgAdmin.FileUtils.transId); - }); - - // Provide initial values for upload form, status, etc. - pgAdmin.FileUtils.setUploader(fileRoot); - - var data; - this.data = data = { - 'Capabilities': capabilities, - }; - - function InputObject() { - this.init = function(cap) { - var self = this, - check_obj = function(path, check) { - - path = decodeURI(path); - if (path.lastIndexOf('/') == path.length - 1 || path.lastIndexOf('\\') == path.length - 1) { - if ( - has_capability(self.data_cap, 'select_folder') - ) { - $('.file_manager_ok').removeClass('disabled'); - $('.file_manager_ok').attr('disabled', false); - $('.file_manager button.delete').removeAttr( - 'disabled', 'disabled' - ); - $('.file_manager button.download').attr( - 'disabled', 'disabled' - ); - $('.file_manager button.rename').attr('disabled', 'disabled'); - // set selected folder name in breadcrums - $('.file_manager #uploader .show_selected_file').remove(); - $('' + path + '').appendTo( - '.file_manager #uploader .filemanager-path-group' - ); - } else { - $('.file_manager_ok').addClass('disabled'); - $('.file_manager_ok').attr('disabled', true); - if (check) { - // Enable/Disable level up button - enab_dis_level_up(); - - $('.file_manager button.delete, .file_manager button.rename').attr('disabled', 'disabled'); - $('.file_manager button.download').attr('disabled', 'disabled'); - getFolderInfo(path); - } - } - } else { - if (has_capability(self.data_cap, 'select_folder')) { - disableSelect(); - } - - if ( - has_capability(self.data_cap, 'select_file') - ) { - $('.file_manager_ok').removeClass('disabled'); - $('.file_manager_ok').attr('disabled', false); - $('.file_manager button.delete, .file_manager button.download, .file_manager button.rename').removeAttr( - 'disabled' - ); - // set selected folder name in breadcrumbs - $('.file_manager #uploader .show_selected_file').remove(); - } - - if (check) { - if (config.options.dialog_type == 'create_file') { - var status = checkPermission(path); - if (status) { - $('.file_manager_ok').trigger('click'); - } - } else if (config.options.dialog_type == 'select_file') { - var file_status = getFileInfo(path); - if (file_status) { - $('.file_manager_ok').trigger('click'); - } - } - } - } - }; - - self.data_cap = cap; - - $('.storage_dialog #uploader .input-path').on('keyup',function(e) { - if (e.keyCode == 13) { - e.stopPropagation(); - var path = $(this).val(); - if (path == '') { - path = '/'; - } - - if (config.options.platform_type === 'win32') { - path = path.replace(/\//g, '\\'); - } else { - path = path.replace(/\\/g, '/'); - if (!path.startsWith('/')) { - path = '/' + path; - } - } - - $(this).val(path); - setTimeout(function() { - check_obj(path, true); - }); - - return; - } - check_obj($(this).val(), false); - }); - }; - this.set_cap = function(cap) { - this.data_cap = cap; - }; - } - var input_object = new InputObject(); - input_object.init(data); - - // Upload file - if (has_capability(data, 'upload')) { - Dropzone.autoDiscover = false; - // we remove simple file upload element - $('.file-input-container').remove(); - $('.upload').remove(); - $('.create').before(' '); - - $('#uploader .upload').off().on('click', function() { - // we create prompt - var msg = '
    ' + - '' + - '
    '+ - '
    '+ - '
    ' + - '
    ' + gettext('Drop files here to upload.') + ' ' + lg.file_size_limit + - config.upload.fileSizeLimit + ' ' + lg.mb + '.
    ', - path = $('.currentpath').val(), - filesizelimit = config.upload.fileSizeLimit, - // default dropzone value - fileSize = (filesizelimit != 'auto') ? filesizelimit : 256, - acceptFiles; - - if (config.security.uploadPolicy == 'DISALLOW_ALL') { - acceptFiles = '.' + config.security.uploadRestrictions.join(',.'); - } else { - // We allow any extension since we have no easy way to handle the the - // built-in `acceptedFiles` params would be handled later by the - // connector. - acceptFiles = null; - } - - $('.file_manager .upload_file').toggleClass('d-none'); - $('.file_manager .file_listing').toggleClass('d-none'); - $('.file_manager .upload_file').html(msg); - - var previewTemplate = '
    '; - - // We need to append our csrf token with dropzone's ajax request header - let csrfToken = {}; - csrfToken[pgAdmin.csrf_token_header] = pgAdmin.csrf_token; - - $('div#multiple-uploads').dropzone({ - paramName: 'newfile', - url: pgAdmin.FileUtils.fileConnector, - headers: csrfToken, - maxFilesize: fileSize, - maxFiles: config.upload.number, - addRemoveLinks: true, - previewTemplate: previewTemplate, - parallelUploads: config.upload.number, - dictMaxFilesExceeded: lg.dz_dictMaxFilesExceeded.replace( - '%s', config.upload.number - ), - dictDefaultMessage: lg.dz_dictDefaultMessage, - dictInvalidFileType: lg.dz_dictInvalidFileType, - dictFileTooBig: lg.file_too_big + ' ' + lg.file_size_limit + - config.upload.fileSizeLimit + ' ' + lg.mb, - acceptedFiles: acceptFiles, - autoProcessQueue: true, - init: function() { - $('.dz_cross_btn').off().on('click', function() { - $('.file_manager .upload_file').toggleClass('d-none'); - $('.file_manager .file_listing').toggleClass('d-none'); - }); - }, - sending: function(file, xhr, formData) { - formData.append('mode', 'add'); - formData.append('currentpath', path); - $('.upload_file .dz_cross_btn').attr('disabled', 'disabled'); - setTimeout(function() {/*This is intentional (SonarQube)*/}, 10000); - }, - success: function(file, response) { - var resp_data = response.data.result, - $this = $(file.previewTemplate); - - if (resp_data.Code == 1) { - setTimeout(function() { - $this.find('.dz-upload').addClass('success'); - }, 1000); - $this.find('.dz-upload').css('width', '100%').html('100%'); - Notify.success(lg.upload_success); - } else { - $this.find('.dz-upload').addClass('error'); - $this.find('.dz-upload').css('width', '0%').html('0%'); - Notify.error(resp_data.Error); - } - getFolderInfo(path); - }, - totaluploadprogress: function() {/*This is intentional (SonarQube)*/}, - complete: function(file) { - if (file.status == 'error') { - Notify.error(lg.upload_error); - } - $('.upload_file .dz_cross_btn').removeAttr('disabled'); - getFolderInfo(path); - }, - }); - }); - } - - this.getDetailView(fileRoot); - }, - /* - * Sets the folder status, upload, and new folder functions - * to the path specified. Called on initial page load and - * whenever a new directory is selected. - */ - setUploader: function(path) { - var config = this.config; - var lg = this.lg; - $('.storage_dialog #uploader').find('a').remove(); - $('.storage_dialog #uploader').find('b').remove(); - - if (config.options.platform_type === 'win32') { - path = path.replace(/\//g, '\\'); - } else { - path = path.replace(/\\/g, '/'); - } - - path = decodeURI(path); - if (config.options.platform_type === 'win32') { - if (config.options.show_volumes && path == '\\') { - $('.storage_dialog #uploader .input-path').val(''); - } else { - $('.storage_dialog #uploader .input-path').val(path); - } - } else if ((config.options.platform_type !== 'win32') && - (path == '' || !path.startsWith('/'))) { - path = '/' + path; - $('.storage_dialog #uploader .input-path').val(path); - } else { - $('.storage_dialog #uploader .input-path').val(path); - } - - if (path.lastIndexOf('\\') == -1 && path.lastIndexOf('/') == -1) { - $('.currentpath').val(path); - } else if (path.lastIndexOf('/') > path.lastIndexOf('\\')) { - $('.currentpath').val(path.substr(0, path.lastIndexOf('/') + 1)); - } else { - $('.currentpath').val(path.substr(0, path.lastIndexOf('\\') + 1)); - } - - enab_dis_level_up(); - if ($('.storage_dialog #uploader h1 span').length === 0) { - $('' + lg.current_folder + '').appendTo($('.storage_dialog #uploader h1')); - } - - $('.storage_dialog #uploader .input-path').attr('title', path); - $('.storage_dialog #uploader .input-path').attr('data-path', path); - enableSelect(); - - // create new folder - $('.create').off().on('click', function() { - var foldername = lg.new_folder; - var $file_element, - $file_element_list, - folder_div; - - - $('.file_manager button.create').attr('disabled', 'disabled'); - $('.no_folder_found').addClass('d-none'); - if ($('.fileinfo').data('view') == 'grid') { - - // template for creating new folder - folder_div = - '
  • ' + - '
    ' + - '
    New_Folder
    ' + - '
  • '; - - path = $('.currentpath').val(); - $file_element = $(folder_div); - $('.fileinfo #contents.grid').prepend($file_element); - $file_element.find('div span.less_text').toggle(); - $file_element.find('div input').toggle().val(lg.new_folder).select(); - - // rename folder/file on pressing enter key - $('.file_manager').on('keyup', function(e) { - if (e.keyCode == 13) { - e.stopPropagation(); - $file_element.find('div input').trigger('blur'); - } - }); - - // rename folder/file on blur - $file_element.find('div input').on('blur', function() { - $('.file_manager button.create').removeAttr('disabled'); - var text_value = $file_element.find('div input').val(); - - path = $('.currentpath').val(); - - $file_element.find('div input').toggle(); - $file_element.find('div span.less_text').toggle().html(text_value); - if (text_value === undefined) { - text_value = lg.new_folder; - } - getFolderName(text_value); - getFolderInfo(path); - }); - - } else if ($('.fileinfo').data('view') == 'list') { - // template to create new folder in table view - folder_div = $( - ` - -
    - -
    -
    - - ${lg.new_folder} -
    -
    -
    - - - - ` - ); - - $file_element_list = $(folder_div); - let tableEl = $('.fileinfo #contents.file_listing_table'); - tableEl.removeClass('file_listing_table_no_data'); - tableEl.find('tbody').prepend($file_element_list); - - $file_element_list.find('td .fm_file_name').toggle(); - $file_element_list.find('td input').toggle().val(lg.new_folder).select(); - - // rename folder/file on pressing enter key - $('.file_manager').on('keyup', function(e) { - if (e.keyCode == 13) { - e.stopPropagation(); - $file_element_list.find('td input').trigger('blur'); - } - }); - - // rename folder/file on blur - $file_element_list.find('td input').on('blur', function() { - $('.file_manager button.create').removeAttr('disabled'); - var text_value = $file_element_list.find('td input').val(); - path = $('.currentpath').val(); - $file_element_list.find('td input').toggle(); - $file_element_list.find('td .fm_file_name span.less_text').html(text_value); - $file_element_list.find('td .fm_file_name').toggle(); - if (text_value === undefined) { - text_value = lg.new_folder; - } - getFolderName(text_value); - getFolderInfo(path); - }); - } - - // create a new folder - var getFolderName = function(value) { - var fname = value; - - if (fname != '') { - foldername = fname; - // Add _ variable in URL for avoiding the caching - $.getJSON( - pgAdmin.FileUtils.fileConnector + '?_=' + Date.now() + '&mode=addfolder&path=' + $('.currentpath').val() + '&name=' + foldername, - function(resp) { - var result = resp.data.result; - if (result.Code === 1) { - Notify.success(lg.successful_added_folder); - getFolderInfo(result.Parent); - } else { - Notify.error(result.Error); - } - } - ); - } else { - Notify.error(lg.no_foldername); - } - }; - - }); - }, - /* Decides whether to retrieve file or folder info based on - * the path provided. - */ - getDetailView: function(path) { - if (path.lastIndexOf('/') == path.length - 1 || path.lastIndexOf('\\') == path.length - 1) { - var allowed_types = this.config.options.allowed_file_types; - - let set_type; - - let response = getFileFormat(this.config.options.allowed_file_types); - let lastSelectedFormat = response.responseJSON.info; - if (_.isUndefined(lastSelectedFormat) || allowed_types.indexOf(lastSelectedFormat) < 0) - set_type = allowed_types[0]; - else - set_type = lastSelectedFormat; - getFolderInfo(path, set_type); - } - }, - // helpful in show/hide toolbar button for Windows - hideButtons: function() { - return ( - this.config.options.platform_type === 'win32' && - $('.currentpath').val() === '' - ); - }, - - }; - return pgAdmin.FileUtils; -}); -//@ sourceURL=utility.js diff --git a/web/pgadmin/misc/file_manager/static/scss/_file_manager.scss b/web/pgadmin/misc/file_manager/static/scss/_file_manager.scss deleted file mode 100644 index 4d15c348c..000000000 --- a/web/pgadmin/misc/file_manager/static/scss/_file_manager.scss +++ /dev/null @@ -1,366 +0,0 @@ -#uploader h1 b { - font-weight: normal; - color: $color-gray; -} - -.file_listing { - min-width: 100%; - position: relative; - overflow: auto; - - .file_listing_table_no_data { - height: auto !important; - } - - .file_listing_table { - table-layout: fixed; - & td, &th { - text-overflow: ellipsis; - white-space: nowrap; - } - } - - .file_listing_table thead tr { - border-bottom: $panel-border; - } - - .file_listing_table tbody tr { - max-width: 100%; - width: 100%; - } - - .file_listing_table tbody tr td:nth-child(1), - .file_listing_table thead tr th:nth-child(1) { - width: 400px; - min-width: 100px; - } - - .file_listing_table tbody tr td:nth-child(2), - .file_listing_table thead tr th:nth-child(2) { - width: 100px; - min-width: 100px; - } - - .file_listing_table tbody tr td:nth-child(3), - .file_listing_table thead tr th:nth-child(3) { - width: 200px; - min-width: 200px; - max-width: 200px; - } -} - -.file_listing #contents.grid li:hover, -.file_listing #contents.grid li.selected { - cursor: pointer; - border: $table-hover-border; - background: $grid-hover-bg-color; - color: $grid-hover-fg-color; -} - -.fileinfo #contents li span.less_text { - width: 100%; - text-overflow: ellipsis; - overflow: hidden; - text-align: center; - white-space: nowrap; - display: block; -} - -.fileinfo table#contents tr td { - font-family: $font-family-primary; - - & span.less_text { - text-overflow: ellipsis; - overflow: hidden; - white-space: nowrap; - display: block; - } - - & .fa { - line-height: inherit; - } -} - -.fm_folder_grid, .fm_file_grid { - font-size: xx-large !important; -} - -.fm_folder_list, -.fm_folder_grid, -.fm_file_grid, -.fm_file_list { - color: $color-fg; -} - -.fm_drive { - font-size: xx-large !important; - color: $color-gray; -} - -.newfile { - position: absolute; - top:0; - left: 3px; - right:0; - width: 152px; - height:23px; - opacity:0; filter: alpha(opacity=0); - cursor: pointer; - border:1px solid $color-primary; -} - -.file_listing #contents.grid li { - display: block; - float: left; - width: 100px; - height: 80px; - text-align: center; - overflow: hidden; - margin: 0.5rem; - -webkit-border-radius: 2px; - -moz-border-radius: 2px; - border-radius: 2px; - border: 1px solid $color-bg; -} - -.file_manager { - position: absolute; - top: 0px; - bottom: 0px; - left: 0px; - right: 0px; -} - -.file_manager #uploader { - border-bottom: $panel-border; -} - -.file_manager #uploader .filemanager-path-group { - padding: 0; - display: block; - border: 1px solid $border-color; - height: 30px; - border-radius: 5px; - -webkit-border-radius: 5px; - -moz-border-radius: 5px; - float: left; - margin-right: 10px; - background: $color-gray-lighter; -} - -.file_manager #uploader .btn-group .btn[disabled] { - color: $color-gray-light; - background-color: $color-gray-lighter; -} - -.file_manager #uploader .filemanager-btn-group { - border: 1px solid $border-color; - border-radius: 5px; - -webkit-border-radius: 5px; - -moz-border-radius: 5px; - width: auto; - float: left; - overflow: hidden; -} - -.file_manager .upload_file #dropzone-container { - background: $color-gray-light; -} - -.fileinfo .prompt-info { - text-align: center; - color: $color-fg; -} - -.allowed_file_types { - border-top: $panel-border; - background: $color-bg; - z-index: 5; - padding: 0.25rem; -} - -.upload_file{ - min-width: 100%; -} - -.upload_file .file_upload_main { - height: 127px; - width: 120px; - display: inline-block; - margin: 0 15px 15px 0 !important; - border: 1px solid $color-bg; - position: relative; - border-radius: 5px; - -webkit-border-radius: 5px; - -moz-border-radius: 5px; - background: $color-bg; - opacity: 1; -} - -.upload_file .file_upload_main .show_error { - padding: 10px 0 0 10px; - color: $color-fg; -} - -.file_upload_main .dz-progress { - float: left; - width: 100%; - height: 21px !important; - border: 1px solid $border-color; - border-radius: 0 !important; - -moz-border-radius: 0 !important; - -webkit-border-radius: 0 !important; -} - -.file_upload_main .dz-progress .dz-upload { - background: $color-primary-light !important; - text-align: center; -} - -.file_upload_main .dz-progress .dz-upload.success { - background: $color-success-light !important; - float: left; - width: 100%; -} - -.upload_file .file_upload_main a.dz_file_remove { - position: absolute; - top: 0; - right: 0; - color: $color-danger; - cursor: pointer; - border-radius: 5px; - -moz-border-radius: 5px; - -webkit-border-radius: 5px; - font-size: large; -} - -.upload_file .file_upload_main a.dz_file_remove:hover { - border: 1px solid $color-fg; -} - -.dropzone .dz-message { - color: $color-gray; -} - -.fileinfo .fm_dimmer { - display: none; - top: 0; - bottom: 0; - background: $loading-bg; - opacity: 0.5; - width: 100%; - position: absolute; - z-index: 3; -} - -.fileinfo .delete_item, .fileinfo .replace_file { - display: none; - padding: 1rem; - border-bottom: $panel-border; - background: $color-bg; - position: absolute; - top: 0; - left: 0; - right: 0; - z-index: 4; -} - -.upload_file .dz_cross_btn { - color: $color-fg; - right: 0px; - position: absolute; - background: transparent; - border: none; -} - -.file_manager .fileinfo #contents .fm_lock_icon { - color: $color-danger; - position: absolute; - top: 6px; - right: 0; - left: 19px; - font-size: 16px; -} - -.file_manager .fileinfo #contents .fa-lock.tbl_lock_icon { - color: $color-danger; - position: relative; - left: -5px; - top: -5px; - font-size: 10px; -} - -.file_manager button.ON { - background: $color-primary; - color: $color-primary-fg; -} - -.fileinfo .is_file_replace { - width: 100%; - height: 100%; - background: $color-gray-lighter; -} - -.file_selection_ctrl button.select_item { - display: inline; - background: $color-bg; - padding: 9px 0px 9px 0px; - margin-left: 0px; - margin-right: -7px; - min-width: 30px; - border-top-left-radius: 0; - border-bottom-left-radius: 0; -} - - -.cap_select_file { - cursor: pointer; -} - -.cap_select_file:hover { - color: $grid-hover-fg-color !important; - .fm_folder_list, - .fm_folder_grid, - .fm_file_grid, - .fm_file_list { - color: $grid-hover-fg-color !important; - } -} - -.add-folder-icon { - position: relative; - top: -8px; - left: -6px; - font-size: 8px; - margin-right: -7px; -} - -table.tablesorter { - th:focus, - tr:focus { - outline: $input-focus-border-color auto 5px !important; - } -} - -#contents { - li:focus { - outline: $input-focus-border-color auto 5px !important; - } -} - -/* Specific to IE11 where we want to highlight the focus on grid/row */ -@media all and (-ms-high-contrast: none), (-ms-high-contrast: active) { - table.tablesorter { - th:focus, - tr:focus { - border: 2px solid $input-focus-border-color !important; - } - } - - #contents { - li:focus { - border: 2px solid $input-focus-border-color !important; - } - } -} diff --git a/web/pgadmin/settings/__init__.py b/web/pgadmin/settings/__init__.py index 178c546a8..688d442a1 100644 --- a/web/pgadmin/settings/__init__.py +++ b/web/pgadmin/settings/__init__.py @@ -23,6 +23,7 @@ from pgadmin.utils.menu import MenuItem from pgadmin.model import db, Setting from pgadmin.utils.constants import MIMETYPE_APP_JS +from .utils import get_dialog_type, get_file_type_setting MODULE_NAME = 'settings' @@ -223,38 +224,20 @@ def get_browser_tree_state(): mimetype="application/json") -def _get_dialog_type(file_type): - """ - This function return dialog type - :param file_type: - :return: dialog type. - """ - if 'pgerd' in file_type: - return 'erd_file_type' - elif 'backup' in file_type: - return 'backup_file_type' - elif 'csv' in file_type and 'txt' in file_type: - return 'import_export_file_type' - elif 'csv' in file_type and 'txt' not in file_type: - return 'storage_manager_file_type' - else: - return 'sqleditor_file_format' - - @blueprint.route("/save_file_format_setting/", endpoint="save_file_format_setting", methods=['POST']) @login_required def save_file_format_setting(): """ - This function save the selected file format. + This function save the selected file format.save_file_format_setting :return: save file format response """ data = request.form if request.form else json.loads( request.data.decode('utf-8')) - file_type = _get_dialog_type(data['allowed_file_types']) + file_type = get_dialog_type(data['allowed_file_types']) - store_setting(file_type, data['selectedFormat']) + store_setting(file_type, data['last_selected_format']) return make_json_response(success=True, info=data, result=request.form) @@ -276,11 +259,5 @@ def get_file_format_setting(): except (ValueError, TypeError, KeyError): data[k] = v - file_type = _get_dialog_type(list(data.values())) - - data = Setting.query.filter_by( - user_id=current_user.id, setting=file_type).first() - if data is None: - return make_json_response(success=True, info='*') - else: - return make_json_response(success=True, info=data.value) + return make_json_response(success=True, + info=get_file_type_setting(list(data.values()))) diff --git a/web/pgadmin/settings/utils.py b/web/pgadmin/settings/utils.py new file mode 100644 index 000000000..69d8e9792 --- /dev/null +++ b/web/pgadmin/settings/utils.py @@ -0,0 +1,36 @@ +from flask_login import current_user +from pgadmin.model import Setting + + +def get_dialog_type(file_type): + """ + This function return dialog type + :param file_type: + :return: dialog type. + """ + if 'pgerd' in file_type: + return 'erd_file_type' + elif 'backup' in file_type: + return 'backup_file_type' + elif 'csv' in file_type and 'txt' in file_type: + return 'import_export_file_type' + elif 'csv' in file_type and 'txt' not in file_type: + return 'storage_manager_file_type' + else: + return 'sqleditor_file_format' + + +def get_file_type_setting(file_types): + """ + This function return last file format setting based on file types + :param file_types: + :return: file format setting. + """ + file_type = get_dialog_type(list(file_types)) + + data = Setting.query.filter_by( + user_id=current_user.id, setting=file_type).first() + if data is None: + return '*' + else: + return data.value diff --git a/web/pgadmin/static/js/SchemaView/DataGridView.jsx b/web/pgadmin/static/js/SchemaView/DataGridView.jsx index 914ac5dd3..9d06a5430 100644 --- a/web/pgadmin/static/js/SchemaView/DataGridView.jsx +++ b/web/pgadmin/static/js/SchemaView/DataGridView.jsx @@ -25,11 +25,11 @@ import _ from 'lodash'; import gettext from 'sources/gettext'; import { SCHEMA_STATE_ACTIONS, StateUtilsContext } from '.'; import FormView, { getFieldMetaData } from './FormView'; -import { confirmDeleteRow } from '../helpers/legacyConnector'; import CustomPropTypes from 'sources/custom_prop_types'; import { evalFunc } from 'sources/utils'; import { DepListenerContext } from './DepListener'; import { useIsMounted } from '../custom_hooks'; +import Notify from '../helpers/Notifier'; const useStyles = makeStyles((theme)=>({ grid: { @@ -303,15 +303,21 @@ export default function DataGridView({ return ( } onClick={()=>{ - confirmDeleteRow(()=>{ - /* Get the changes on dependent fields as well */ - dataDispatch({ - type: SCHEMA_STATE_ACTIONS.DELETE_ROW, - path: accessPath, - value: row.index, - }); - - }, ()=>{/*This is intentional (SonarQube)*/}, props.customDeleteTitle, props.customDeleteMsg); + Notify.confirm( + props.customDeleteTitle || gettext('Delete Row'), + props.customDeleteMsg || gettext('Are you sure you wish to delete this row?'), + function() { + dataDispatch({ + type: SCHEMA_STATE_ACTIONS.DELETE_ROW, + path: accessPath, + value: row.index, + }); + return true; + }, + function() { + return true; + } + ); }} className={classes.gridRowButton} disabled={!canDeleteRow} /> ); } diff --git a/web/pgadmin/static/js/Theme/index.jsx b/web/pgadmin/static/js/Theme/index.jsx index 1f6be3d4c..4b966f881 100644 --- a/web/pgadmin/static/js/Theme/index.jsx +++ b/web/pgadmin/static/js/Theme/index.jsx @@ -125,6 +125,9 @@ basicSettings = createMuiTheme(basicSettings, { }, adornedEnd: { paddingRight: basicSettings.spacing(0.75), + }, + marginDense: { + height: '28px', } }, MuiAccordion: { diff --git a/web/pgadmin/static/js/backform.pgadmin.js b/web/pgadmin/static/js/backform.pgadmin.js index 0f0a8ab4d..3368111cf 100644 --- a/web/pgadmin/static/js/backform.pgadmin.js +++ b/web/pgadmin/static/js/backform.pgadmin.js @@ -2835,106 +2835,6 @@ define([ ].join('\n')), }); - /* - * Input File Control: This control is used with Storage Manager Dialog, - * It allows user to perform following operations: - * - Select File - * - Select Folder - * - Create File - * - Opening Storage Manager Dialog itself. - */ - Backform.FileControl = Backform.InputControl.extend({ - defaults: { - type: 'text', - label: '', - min: undefined, - max: undefined, - maxlength: 255, - extraClasses: [], - dialog_title: '', - btn_primary: '', - helpMessage: null, - dialog_type: 'select_file', - }, - initialize: function() { - Backform.InputControl.prototype.initialize.apply(this, arguments); - }, - template: _.template([ - '', - '
    ', - '
    ', - ' <%=readonly ? "readonly aria-readonly=true" : ""%> <%=required ? "required" : ""%> />', - '
    ', - '', - '
    ', - '
    ', - '<% if (helpMessage && helpMessage.length) { %>', - '<%=helpMessage%>', - '<% } %>', - '
    ', - ].join('\n')), - events: function() { - // Inherit all default events of InputControl - return _.extend({}, Backform.InputControl.prototype.events, { - 'click .select_item': 'onSelect', - }); - }, - onSelect: function() { - var dialog_type = this.field.get('dialog_type'), - supp_types = this.field.get('supp_types'), - btn_primary = this.field.get('btn_primary'), - dialog_title = this.field.get('dialog_title'), - params = { - supported_types: supp_types, - dialog_type: dialog_type, - dialog_title: dialog_title, - btn_primary: btn_primary, - }; - - pgAdmin.FileManager.init(); - pgAdmin.FileManager.show_dialog(params); - // Listen click events of Storage Manager dialog buttons - this.listen_file_dlg_events(); - }, - storage_dlg_hander: function(value) { - var attrArr = this.field.get('name').split('.'), - name = attrArr.shift(); - - this.remove_file_dlg_event_listeners(); - - // Set selected value into the model - this.model.set(name, decodeURI(value)); - this.$el.find('input[type=text]').focus(); - }, - storage_close_dlg_hander: function() { - this.remove_file_dlg_event_listeners(); - }, - listen_file_dlg_events: function() { - pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:' + this.field.get('dialog_type'), this.storage_dlg_hander, this); - pgAdmin.Browser.Events.on('pgadmin-storage:cancel_btn:' + this.field.get('dialog_type'), this.storage_close_dlg_hander, this); - }, - remove_file_dlg_event_listeners: function() { - pgAdmin.Browser.Events.off('pgadmin-storage:finish_btn:' + this.field.get('dialog_type'), this.storage_dlg_hander, this); - pgAdmin.Browser.Events.off('pgadmin-storage:cancel_btn:' + this.field.get('dialog_type'), this.storage_close_dlg_hander, this); - }, - clearInvalid: function() { - Backform.InputControl.prototype.clearInvalid.apply(this, arguments); - this.$el.removeClass('pgadmin-file-has-error'); - return this; - }, - updateInvalid: function() { - Backform.InputControl.prototype.updateInvalid.apply(this, arguments); - // Introduce a new class to fix the error icon placement on the control - this.$el.addClass('pgadmin-file-has-error'); - }, - disable_button: function() { - this.$el.find('button.select_item').attr('disabled', 'disabled'); - }, - enable_button: function() { - this.$el.find('button.select_item').removeAttr('disabled'); - }, - }); - Backform.DatetimepickerControl = Backform.InputControl.extend({ defaults: { diff --git a/web/pgadmin/static/js/backgrid.pgadmin.js b/web/pgadmin/static/js/backgrid.pgadmin.js index b997a0c69..0eadfa606 100644 --- a/web/pgadmin/static/js/backgrid.pgadmin.js +++ b/web/pgadmin/static/js/backgrid.pgadmin.js @@ -12,10 +12,10 @@ import Notify from '../../static/js/helpers/Notifier'; define([ 'sources/gettext', 'underscore', 'jquery', 'backbone', 'backform', 'backgrid', 'alertify', 'moment', 'bignumber', 'codemirror', 'sources/utils', 'sources/keyboard_shortcuts', 'sources/select2/configure_show_on_scroll', - 'sources/window', 'sources/url_for', 'bootstrap.datetimepicker', 'backgrid.filter', 'bootstrap.toggle', + 'sources/window', 'bootstrap.datetimepicker', 'backgrid.filter', 'bootstrap.toggle', ], function( gettext, _, $, Backbone, Backform, Backgrid, Alertify, moment, BigNumber, CodeMirror, - commonUtils, keyboardShortcuts, configure_show_on_scroll, pgWindow, url_for + commonUtils, keyboardShortcuts, configure_show_on_scroll, pgWindow ) { /* * Add mechanism in backgrid to render different types of cells in @@ -2314,125 +2314,5 @@ define([ }, }); - Backgrid.Extension.SelectFileCell = Backgrid.Cell.extend({ - /** @property */ - className: 'file-cell', - defaults: { - supported_types: ['*'], - dialog_type: 'select_file', - dialog_title: gettext('Select file'), - type: 'text', - value: '', - placeholder: gettext('Select file...'), - disabled: false, - browse_btn_label: gettext('Select file'), - check_btn_label: gettext('Validate file'), - browse_btn_visible: true, - validate_btn_visible: true, - }, - - initialize: function() { - Backgrid.Cell.prototype.initialize.apply(this, arguments); - this.data = _.extend(this.defaults, this.column.toJSON()); - }, - template: _.template([ - '
    ', - ' />', - '<% if (browse_btn_visible) { %>', - '
    ', - '', - '
    ', - '<% } %>', - '<% if (validate_btn_visible) { %>', - '
    ', - '', - '
    ', - '<% } %>', - '
    ', - ].join('\n')), - events: { - 'change input': 'onChange', - 'click .select_item': 'onSelect', - 'click .validate_item': 'onValidate', - }, - - render: function() { - this.$el.empty(); - this.data = _.extend(this.data, {value: this.model.get(this.column.get('name'))}); - // Adding unique id - this.data['cId'] = _.uniqueId('pgC_'); - this.$el.append(this.template(this.data)); - - this.$input = this.$el.find('input'); - this.delegateEvents(); - - return this; - }, - onChange: function() { - var model = this.model, - column = this.column, - val = this.formatter.toRaw(this.$input.prop('value'), model); - - model.set(column.get('name'), val); - }, - onSelect: function() { - let self = this; - - var params = { - supported_types: self.data.supported_types, - dialog_type: self.data.dialog_type, - dialog_title: self.data.dialog_title - }; - - pgAdmin.FileManager.init(); - pgAdmin.FileManager.show_dialog(params); - // Listen click events of Storage Manager dialog buttons - this.listen_file_dlg_events(); - }, - storage_dlg_hander: function(value) { - var attrArr = this.column.get('name').split('.'), - name = attrArr.shift(); - - this.remove_file_dlg_event_listeners(); - - // Set selected value into the model - this.model.set(name, decodeURI(value)); - }, - storage_close_dlg_hander: function() { - this.remove_file_dlg_event_listeners(); - }, - listen_file_dlg_events: function() { - pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:' + this.data.dialog_type, this.storage_dlg_hander, this); - pgAdmin.Browser.Events.on('pgadmin-storage:cancel_btn:' + this.data.dialog_type, this.storage_close_dlg_hander, this); - }, - remove_file_dlg_event_listeners: function() { - pgAdmin.Browser.Events.off('pgadmin-storage:finish_btn:' + this.data.dialog_type, this.storage_dlg_hander, this); - pgAdmin.Browser.Events.off('pgadmin-storage:cancel_btn:' + this.data.dialog_type, this.storage_close_dlg_hander, this); - }, - onValidate: function() { - var model = this.model, - val = this.formatter.toRaw(this.$input.prop('value'), model); - - if (_.isNull(val) || val.trim() === '') { - Notify.alert(gettext('Validate Path'), gettext('Path should not be empty.')); - } - - $.ajax({ - url: url_for('misc.validate_binary_path'), - method: 'POST', - contentType: 'application/json', - data: JSON.stringify({ - 'utility_path': val, - }), - }) - .done(function(res) { - Notify.alert(gettext('Validate binary path'), gettext(res.data)); - }) - .fail(function(xhr, error) { - Notify.pgNotifier(error, xhr, gettext('Failed to validate binary path.')); - }); - }, - }); - return Backgrid; }); diff --git a/web/pgadmin/static/js/components/Buttons.jsx b/web/pgadmin/static/js/components/Buttons.jsx index c15e313d5..c446926c5 100644 --- a/web/pgadmin/static/js/components/Buttons.jsx +++ b/web/pgadmin/static/js/components/Buttons.jsx @@ -199,7 +199,7 @@ PgIconButton.propTypes = { export const PgButtonGroup = forwardRef(({children, ...props}, ref)=>{ /* Tooltip does not work for disabled items */ return ( - + {children} ); diff --git a/web/pgadmin/static/js/components/FormComponents.jsx b/web/pgadmin/static/js/components/FormComponents.jsx index cb78020b1..2dcd79d69 100644 --- a/web/pgadmin/static/js/components/FormComponents.jsx +++ b/web/pgadmin/static/js/components/FormComponents.jsx @@ -35,13 +35,13 @@ import * as DateFns from 'date-fns'; import CodeMirror from './CodeMirror'; import gettext from 'sources/gettext'; -import { showFileDialog } from '../helpers/legacyConnector'; import _ from 'lodash'; import { DefaultButton, PrimaryButton, PgIconButton } from './Buttons'; import CustomPropTypes from '../custom_prop_types'; import KeyboardShortcuts from './KeyboardShortcuts'; import QueryThresholds from './QueryThresholds'; import SelectThemes from './SelectThemes'; +import { showFileManager } from '../helpers/showFileManager'; const useStyles = makeStyles((theme) => ({ @@ -326,11 +326,10 @@ FormInputDateTimePicker.propTypes = { /* Use forwardRef to pass ref prop to OutlinedInput */ export const InputText = forwardRef(({ - cid, helpid, readonly, disabled, value, onChange, controlProps, type, ...props }, ref) => { + cid, helpid, readonly, disabled, value, onChange, controlProps, type, size, ...props }, ref) => { const maxlength = typeof(controlProps?.maxLength) != 'undefined' ? controlProps.maxLength : 255; - const classes = useStyles(); const patterns = { 'numeric': '^-?[0-9]\\d*\\.?\\d*$', 'int': '^-?[0-9]\\d*$', @@ -356,12 +355,17 @@ export const InputText = forwardRef(({ finalValue = controlProps.formatter.fromRaw(finalValue); } + const filteredProps = _.pickBy(props, (_v, key)=>( + /* When used in ButtonGroup, following props should be skipped */ + !['color', 'disableElevation', 'disableFocusRipple', 'disableRipple'].includes(key) + )); + return ( -1 ? { type: 'tel' } : { type: type })} /> ); @@ -394,6 +398,7 @@ InputText.propTypes = { onChange: PropTypes.func, controlProps: PropTypes.object, type: PropTypes.string, + size: PropTypes.string, }; export function FormInputText({ hasError, required, label, className, helpMessage, testcid, ...props }) { @@ -412,7 +417,6 @@ FormInputText.propTypes = { testcid: PropTypes.string, }; -/* Using the existing file dialog functions using showFileDialog */ export function InputFileSelect({ controlProps, onChange, disabled, readonly, isvalidate = false, hideBrowseButton=false,validate, ...props }) { const inpRef = useRef(); let textControlProps = {}; @@ -420,15 +424,24 @@ export function InputFileSelect({ controlProps, onChange, disabled, readonly, is const {placeholder} = controlProps; textControlProps = {placeholder}; } - const onFileSelect = (value) => { - onChange && onChange(decodeURI(value)); - inpRef.current.focus(); + const showFileDialog = ()=>{ + let params = { + supported_types: controlProps.supportedTypes || [], + dialog_type: controlProps.dialogType || 'select_file', + dialog_title: controlProps.dialogTitle || '', + btn_primary: controlProps.btnPrimary || '', + }; + showFileManager(params, (fileName)=>{ + onChange && onChange(decodeURI(fileName)); + inpRef.current.focus(); + }); }; + return ( {!hideBrowseButton && - showFileDialog(controlProps, onFileSelect)} + } {isvalidate && @@ -1184,6 +1197,9 @@ const useStylesFormFooter = makeStyles((theme) => ({ message: { marginLeft: theme.spacing(0.5), }, + messageCenter: { + margin: 'auto', + }, closeButton: { marginLeft: 'auto', }, @@ -1272,13 +1288,13 @@ FormInputSelectThemes.propTypes = { }; -export function NotifierMessage({ type = MESSAGE_TYPE.SUCCESS, message, closable = true, onClose = () => {/*This is intentional (SonarQube)*/ } }) { +export function NotifierMessage({ type = MESSAGE_TYPE.SUCCESS, message, closable = true, showIcon=true, textCenter=false, onClose = () => {/*This is intentional (SonarQube)*/ } }) { const classes = useStylesFormFooter(); return ( - - {HTMLReactParse(message || '')} + {showIcon && } + {HTMLReactParse(message || '')} {closable && } @@ -1290,6 +1306,8 @@ NotifierMessage.propTypes = { type: PropTypes.oneOf(Object.values(MESSAGE_TYPE)).isRequired, message: PropTypes.string, closable: PropTypes.bool, + showIcon: PropTypes.bool, + textCenter: PropTypes.bool, onClose: PropTypes.func, }; diff --git a/web/pgadmin/static/js/components/PgReactDataGrid.jsx b/web/pgadmin/static/js/components/PgReactDataGrid.jsx new file mode 100644 index 000000000..210d8c980 --- /dev/null +++ b/web/pgadmin/static/js/components/PgReactDataGrid.jsx @@ -0,0 +1,88 @@ +import React from 'react'; +import ReactDataGrid from 'react-data-grid'; +import { makeStyles } from '@material-ui/core'; +import clsx from 'clsx'; +import PropTypes from 'prop-types'; +import CustomPropTypes from '../custom_prop_types'; + +const useStyles = makeStyles((theme)=>({ + root: { + height: '100%', + color: theme.palette.text.primary, + backgroundColor: theme.otherVars.qtDatagridBg, + fontSize: '12px', + border: 'none', + '--rdg-selection-color': theme.palette.primary.main, + '& .rdg-cell': { + ...theme.mixins.panelBorder.right, + ...theme.mixins.panelBorder.bottom, + fontWeight: 'abc', + '&[aria-colindex="1"]': { + padding: 0, + }, + '&[aria-selected=true]:not([role="columnheader"])': { + outlineWidth: '0px', + outlineOffset: '0px', + } + }, + '& .rdg-header-row .rdg-cell': { + padding: 0, + }, + '& .rdg-header-row': { + backgroundColor: theme.palette.background.default, + fontWeight: 'normal', + }, + '& .rdg-row': { + backgroundColor: theme.palette.background.default, + '&[aria-selected=true]': { + backgroundColor: theme.palette.primary.light, + color: theme.otherVars.qtDatagridSelectFg, + }, + } + }, + cellSelection: { + '& .rdg-cell': { + '&[aria-selected=true]:not([role="columnheader"])': { + outlineWidth: '1px', + outlineOffset: '-1px', + backgroundColor: theme.palette.primary.light, + color: theme.otherVars.qtDatagridSelectFg, + } + }, + }, + hasSelectColumn: { + '& .rdg-cell': { + '&[aria-selected=true][aria-colindex="1"]': { + outlineWidth: '2px', + outlineOffset: '-2px', + backgroundColor: theme.otherVars.qtDatagridBg, + color: theme.palette.text.primary, + } + }, + '& .rdg-row[aria-selected=true] .rdg-cell:nth-child(1)': { + backgroundColor: theme.palette.primary.main, + color: theme.palette.primary.contrastText, + } + } +})); + + +export default function PgReactDataGrid({gridRef, className, hasSelectColumn=true, ...props}) { + const classes = useStyles(); + let finalClassName = [classes.root]; + hasSelectColumn && finalClassName.push(classes.hasSelectColumn); + props.enableCellSelect && finalClassName.push(classes.cellSelection); + finalClassName.push(className); + return ; +} + +PgReactDataGrid.propTypes = { + gridRef: CustomPropTypes.ref, + className: CustomPropTypes.className, + hasSelectColumn: PropTypes.bool, + enableCellSelect: PropTypes.bool, +}; diff --git a/web/pgadmin/static/js/helpers/ModalProvider.jsx b/web/pgadmin/static/js/helpers/ModalProvider.jsx index 80523fe04..510cb96dc 100644 --- a/web/pgadmin/static/js/helpers/ModalProvider.jsx +++ b/web/pgadmin/static/js/helpers/ModalProvider.jsx @@ -22,7 +22,7 @@ import CheckRoundedIcon from '@material-ui/icons/CheckRounded'; import { Rnd } from 'react-rnd'; import { ExpandDialogIcon, MinimizeDialogIcon } from '../components/ExternalIcon'; -const ModalContext = React.createContext({}); +export const ModalContext = React.createContext({}); const MIN_HEIGHT = 190; const MIN_WIDTH = 500; diff --git a/web/pgadmin/static/js/helpers/legacyConnector.js b/web/pgadmin/static/js/helpers/legacyConnector.js deleted file mode 100644 index adc7c27d6..000000000 --- a/web/pgadmin/static/js/helpers/legacyConnector.js +++ /dev/null @@ -1,65 +0,0 @@ -///////////////////////////////////////////////////////////// -// -// pgAdmin 4 - PostgreSQL Tools -// -// Copyright (C) 2013 - 2022, The pgAdmin Development Team -// This software is released under the PostgreSQL Licence -// -////////////////////////////////////////////////////////////// - -/* This file will have wrappers and connectors used by React components to - * re-use any existing non-react components. - * These functions may not be needed once all are migrated - */ - -import gettext from 'sources/gettext'; -import pgAdmin from 'sources/pgadmin'; -import Notify from './Notifier'; - -export function confirmDeleteRow(onOK, onCancel, title, message) { - Notify.confirm( - title || gettext('Delete Row'), - message || gettext('Are you sure you wish to delete this row?'), - function() { - onOK(); - return true; - }, - function() { - onCancel(); - return true; - } - ); -} - -/* Used by file select component to re-use existing logic */ -export function showFileDialog(dialogParams, onFileSelect) { - let params = { - supported_types: dialogParams.supportedTypes || [], - dialog_type: dialogParams.dialogType || 'select_file', - dialog_title: dialogParams.dialogTitle || '', - btn_primary: dialogParams.btnPrimary || '', - }; - pgAdmin.FileManager.init(); - pgAdmin.FileManager.show_dialog(params); - - const onFileSelectClose = (value)=>{ - removeListeners(); - onFileSelect(value); - }; - const onDialogClose = ()=>removeListeners(); - pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:' + params.dialog_type, onFileSelectClose); - pgAdmin.Browser.Events.on('pgadmin-storage:cancel_btn:' + params.dialog_type, onDialogClose); - - const removeListeners = ()=>{ - pgAdmin.Browser.Events.off('pgadmin-storage:finish_btn:' + params.dialog_type, onFileSelectClose); - pgAdmin.Browser.Events.off('pgadmin-storage:cancel_btn:' + params.dialog_type, onDialogClose); - }; -} - -export function onPgadminEvent(eventName, handler) { - pgAdmin.Browser.Events.on(eventName, handler); -} - -export function offPgadminEvent(eventName, handler) { - pgAdmin.Browser.Events.off(eventName, handler); -} diff --git a/web/pgadmin/static/js/helpers/showFileManager.js b/web/pgadmin/static/js/helpers/showFileManager.js new file mode 100644 index 000000000..fc658920c --- /dev/null +++ b/web/pgadmin/static/js/helpers/showFileManager.js @@ -0,0 +1,6 @@ +import pgAdmin from 'sources/pgadmin'; +import 'pgadmin.tools.file_manager'; + +export function showFileManager(...args) { + pgAdmin.Tools.FileManager.show(...args); +} diff --git a/web/pgadmin/static/js/tree/tree.js b/web/pgadmin/static/js/tree/tree.js index 839016adf..467822b9f 100644 --- a/web/pgadmin/static/js/tree/tree.js +++ b/web/pgadmin/static/js/tree/tree.js @@ -14,8 +14,6 @@ import pgAdmin from 'sources/pgadmin'; import { FileType } from 'react-aspen'; import { TreeNode } from './tree_nodes'; -import { isValidData } from 'sources/utils'; - function manageTreeEvents(event, eventName, item) { let d = item ? item._metadata.data : []; let node_metadata = item ? item._metadata : {}; @@ -594,6 +592,6 @@ export function findInTree(rootNode, path) { })(rootNode); } -let isValidTreeNodeData = isValidData; +let isValidTreeNodeData = (data) => (!_.isEmpty(data)); export { isValidTreeNodeData }; diff --git a/web/pgadmin/static/js/utils.js b/web/pgadmin/static/js/utils.js index 0602921d4..5f5134834 100644 --- a/web/pgadmin/static/js/utils.js +++ b/web/pgadmin/static/js/utils.js @@ -7,7 +7,7 @@ // ////////////////////////////////////////////////////////////////////////// -import _ from 'underscore'; +import _ from 'lodash'; import $ from 'jquery'; import gettext from 'sources/gettext'; import 'wcdocker'; @@ -115,14 +115,6 @@ export function findAndSetFocus(container) { }, 200); } -let isValidData = (data) => (!_.isUndefined(data) && !_.isNull(data)); -let isFunction = (fn) => (_.isFunction(fn)); -let isString = (str) => (_.isString(str)); - -export { - isValidData, isFunction, isString, -}; - export function getEpoch(inp_date) { let date_obj = inp_date ? inp_date : new Date(); return parseInt(date_obj.getTime()/1000); @@ -456,6 +448,10 @@ export function getBrowser() { tem=/\brv[ :]+(\d+)/g.exec(ua) || []; return {name:'IE', version:(tem[1]||'')}; } + if(ua.startsWith('Nwjs')) { + let nwjs = ua.split('-')[0]?.split(':'); + return {name:nwjs[0], version: nwjs[1]}; + } if(M[1]==='Chrome') { tem=ua.match(/\bOPR|Edge\/(\d+)/); @@ -480,3 +476,21 @@ export function checkTrojanSource(content, isPasteEvent) { Notify.alert(gettext('Trojan Source Warning'), msg); } } + +export function downloadBlob(blob, fileName) { + let urlCreator = window.URL || window.webkitURL, + downloadUrl = urlCreator.createObjectURL(blob), + link = document.createElement('a'); + + document.body.appendChild(link); + + if (getBrowser() === 'IE' && window.navigator.msSaveBlob) { + // IE10+ : (has Blob, but not a[download] or URL) + window.navigator.msSaveBlob(blob, fileName); + } else { + link.setAttribute('href', downloadUrl); + link.setAttribute('download', fileName); + link.click(); + } + document.body.removeChild(link); +} diff --git a/web/pgadmin/tools/__init__.py b/web/pgadmin/tools/__init__.py index 711699a89..9ab20d574 100644 --- a/web/pgadmin/tools/__init__.py +++ b/web/pgadmin/tools/__init__.py @@ -64,9 +64,6 @@ class ToolsModule(PgAdminModule): from .sqleditor import blueprint as module app.register_blueprint(module) - from .storage_manager import blueprint as module - app.register_blueprint(module) - from .user_management import blueprint as module app.register_blueprint(module) diff --git a/web/pgadmin/tools/erd/static/js/erd_tool/index.js b/web/pgadmin/tools/erd/static/js/erd_tool/index.js index 8563ac562..1c7a10d12 100644 --- a/web/pgadmin/tools/erd/static/js/erd_tool/index.js +++ b/web/pgadmin/tools/erd/static/js/erd_tool/index.js @@ -17,6 +17,9 @@ import Alertify from 'pgadmin.alertifyjs'; import pgWindow from 'sources/window'; import pgAdmin from 'sources/pgadmin'; +import ModalProvider from '../../../../../static/js/helpers/ModalProvider'; +import Theme from '../../../../../static/js/Theme'; + export default class ERDTool { constructor(container, params) { this.container = document.querySelector(container); @@ -37,13 +40,17 @@ export default class ERDTool { }); ReactDOM.render( - , + + + + + , this.container ); } diff --git a/web/pgadmin/tools/erd/static/js/erd_tool/ui_components/BodyWidget.jsx b/web/pgadmin/tools/erd/static/js/erd_tool/ui_components/BodyWidget.jsx index 4132ae1e9..6427292d3 100644 --- a/web/pgadmin/tools/erd/static/js/erd_tool/ui_components/BodyWidget.jsx +++ b/web/pgadmin/tools/erd/static/js/erd_tool/ui_components/BodyWidget.jsx @@ -27,6 +27,7 @@ import 'wcdocker'; import Theme from '../../../../../../static/js/Theme'; import TableSchema from '../../../../../../browser/server_groups/servers/databases/schemas/tables/static/js/table.ui'; import Notify from '../../../../../../static/js/helpers/Notifier'; +import { ModalContext } from '../../../../../../static/js/helpers/ModalProvider'; /* Custom react-diagram action for keyboard events */ export class KeyboardShortcutAction extends Action { @@ -61,6 +62,7 @@ export class KeyboardShortcutAction extends Action { /* The main body container for the ERD */ export default class BodyWidget extends React.Component { + static contextType = ModalContext; constructor() { super(); this.state = { @@ -214,8 +216,6 @@ export default class BodyWidget extends React.Component { backgroundPosition: '0px 0px', }); - this.props.pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:select_file', this.openFile, this); - this.props.pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:create_file', this.saveFile, this); this.props.pgAdmin.Browser.onPreferencesChange('erd', () => { this.setState({ preferences: this.props.pgWindow.pgAdmin.Browser.get_preferences_for_module('erd'), @@ -468,11 +468,10 @@ export default class BodyWidget extends React.Component { onLoadDiagram() { var params = { - 'supported_types': ['pgerd'], // file types allowed + 'supported_types': ['*','pgerd'], // file types allowed 'dialog_type': 'select_file', // open select file dialog }; - this.props.pgAdmin.FileManager.init(); - this.props.pgAdmin.FileManager.show_dialog(params); + this.props.pgAdmin.Tools.FileManager.show(params, this.openFile.bind(this), null, this.context); } openFile(fileName) { @@ -501,13 +500,12 @@ export default class BodyWidget extends React.Component { this.saveFile(this.state.current_file); } else { var params = { - 'supported_types': ['pgerd'], + 'supported_types': ['*','pgerd'], 'dialog_type': 'create_file', 'dialog_title': 'Save File', 'btn_primary': 'Save', }; - this.props.pgAdmin.FileManager.init(); - this.props.pgAdmin.FileManager.show_dialog(params); + this.props.pgAdmin.Tools.FileManager.show(params, this.saveFile.bind(this), null, this.context); } } diff --git a/web/pgadmin/tools/erd/static/js/erd_tool_hook.js b/web/pgadmin/tools/erd/static/js/erd_tool_hook.js index 9fa0a2e3a..dafc69afd 100644 --- a/web/pgadmin/tools/erd/static/js/erd_tool_hook.js +++ b/web/pgadmin/tools/erd/static/js/erd_tool_hook.js @@ -10,7 +10,7 @@ define([ 'sources/pgadmin', 'pgadmin.tools.erd/erd_tool', 'pgadmin.browser', 'pgadmin.browser.server.privilege', 'pgadmin.node.database', 'pgadmin.node.primary_key', - 'pgadmin.node.foreign_key', 'pgadmin.browser.datamodel', 'pgadmin.file_manager', + 'pgadmin.node.foreign_key', 'pgadmin.browser.datamodel', 'pgadmin.tools.file_manager', ], function( pgAdmin, ERDToolModule ) { diff --git a/web/pgadmin/tools/import_export_servers/static/js/import_export_servers.js b/web/pgadmin/tools/import_export_servers/static/js/import_export_servers.js index d2953a3d2..b436b79cf 100644 --- a/web/pgadmin/tools/import_export_servers/static/js/import_export_servers.js +++ b/web/pgadmin/tools/import_export_servers/static/js/import_export_servers.js @@ -9,7 +9,6 @@ import React from 'react'; import ReactDOM from 'react-dom'; -import 'pgadmin.file_manager'; import gettext from 'sources/gettext'; import Alertify from 'pgadmin.alertifyjs'; import Theme from 'sources/Theme'; diff --git a/web/pgadmin/tools/sqleditor/static/js/SQLEditorModule.js b/web/pgadmin/tools/sqleditor/static/js/SQLEditorModule.js index fcf606254..33587d7e5 100644 --- a/web/pgadmin/tools/sqleditor/static/js/SQLEditorModule.js +++ b/web/pgadmin/tools/sqleditor/static/js/SQLEditorModule.js @@ -20,8 +20,8 @@ var wcDocker = window.wcDocker; import pgWindow from 'sources/window'; import pgAdmin from 'sources/pgadmin'; import pgBrowser from 'pgadmin.browser'; -import 'pgadmin.file_manager'; import 'pgadmin.tools.user_management'; +import 'pgadmin.tools.file_manager'; import gettext from 'sources/gettext'; import React from 'react'; import ReactDOM from 'react-dom'; diff --git a/web/pgadmin/tools/sqleditor/static/js/components/QueryToolComponent.jsx b/web/pgadmin/tools/sqleditor/static/js/components/QueryToolComponent.jsx index 71b5bb16c..86966c73b 100644 --- a/web/pgadmin/tools/sqleditor/static/js/components/QueryToolComponent.jsx +++ b/web/pgadmin/tools/sqleditor/static/js/components/QueryToolComponent.jsx @@ -332,15 +332,6 @@ export default function QueryToolComponent({params, pgWindow, pgAdmin, selectedN } } }); - - pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:select_file', (fileName)=>{ - eventBus.current.fireEvent(QUERY_TOOL_EVENTS.LOAD_FILE, fileName); - }, pgAdmin); - - pgAdmin.Browser.Events.on('pgadmin-storage:finish_btn:create_file', (fileName)=>{ - eventBus.current.fireEvent(QUERY_TOOL_EVENTS.SAVE_FILE, fileName); - }, pgAdmin); - window.addEventListener('beforeunload', onBeforeUnload); }, []); @@ -428,8 +419,9 @@ export default function QueryToolComponent({params, pgWindow, pgAdmin, selectedN 'supported_types': ['*', 'sql'], // file types allowed 'dialog_type': 'select_file', // open select file dialog }; - pgAdmin.FileManager.init(); - pgAdmin.FileManager.show_dialog(fileParams); + pgAdmin.Tools.FileManager.show(fileParams, (fileName)=>{ + eventBus.current.fireEvent(QUERY_TOOL_EVENTS.LOAD_FILE, fileName); + }, null, modal); }], [QUERY_TOOL_EVENTS.TRIGGER_SAVE_FILE, (isSaveAs=false)=>{ if(!isSaveAs && qtState.current_file) { @@ -441,8 +433,9 @@ export default function QueryToolComponent({params, pgWindow, pgAdmin, selectedN 'dialog_title': 'Save File', 'btn_primary': 'Save', }; - pgAdmin.FileManager.init(); - pgAdmin.FileManager.show_dialog(fileParams); + pgAdmin.Tools.FileManager.show(fileParams, (fileName)=>{ + eventBus.current.fireEvent(QUERY_TOOL_EVENTS.SAVE_FILE, fileName); + }, null, modal); } }], [QUERY_TOOL_EVENTS.LOAD_FILE_DONE, fileDone], diff --git a/web/pgadmin/tools/sqleditor/static/js/components/QueryToolDataGrid/index.jsx b/web/pgadmin/tools/sqleditor/static/js/components/QueryToolDataGrid/index.jsx index 5e51c6b4b..23c42a711 100644 --- a/web/pgadmin/tools/sqleditor/static/js/components/QueryToolDataGrid/index.jsx +++ b/web/pgadmin/tools/sqleditor/static/js/components/QueryToolDataGrid/index.jsx @@ -9,7 +9,7 @@ import { Box, makeStyles } from '@material-ui/core'; import _ from 'lodash'; import React, {useState, useEffect, useContext, useRef, useLayoutEffect} from 'react'; -import ReactDataGrid, {Row, useRowSelection} from 'react-data-grid'; +import {Row, useRowSelection} from 'react-data-grid'; import LockIcon from '@material-ui/icons/Lock'; import EditIcon from '@material-ui/icons/Edit'; import { QUERY_TOOL_EVENTS } from '../QueryToolConstants'; @@ -21,51 +21,12 @@ import MapIcon from '@material-ui/icons/Map'; import { QueryToolEventsContext } from '../QueryToolComponent'; import PropTypes from 'prop-types'; import gettext from 'sources/gettext'; +import PgReactDataGrid from '../../../../../../static/js/components/PgReactDataGrid'; export const ROWNUM_KEY = '$_pgadmin_rownum_key_$'; export const GRID_ROW_SELECT_KEY = '$_pgadmin_gridrowselect_key_$'; const useStyles = makeStyles((theme)=>({ - root: { - height: '100%', - color: theme.palette.text.primary, - backgroundColor: theme.otherVars.qtDatagridBg, - fontSize: '12px', - border: 'none', - '--rdg-selection-color': theme.palette.primary.main, - '& .rdg-cell': { - ...theme.mixins.panelBorder.right, - ...theme.mixins.panelBorder.bottom, - fontWeight: 'abc', - '&[aria-colindex="1"]': { - padding: 0, - }, - '&[aria-selected=true]:not([role="columnheader"]):not([aria-colindex="1"])': { - outlineWidth: '1px', - outlineOffset: '-1px', - backgroundColor: theme.palette.primary.light, - color: theme.otherVars.qtDatagridSelectFg, - } - }, - '& .rdg-header-row .rdg-cell': { - padding: 0, - }, - '& .rdg-header-row': { - backgroundColor: theme.palette.background.default, - fontWeight: 'normal', - }, - '& .rdg-row': { - backgroundColor: theme.palette.background.default, - '&[aria-selected=true]': { - backgroundColor: theme.palette.primary.light, - color: theme.otherVars.qtDatagridSelectFg, - '& .rdg-cell:nth-child(1)': { - backgroundColor: theme.palette.primary.main, - color: theme.palette.primary.contrastText, - } - }, - } - }, columnHeader: { padding: '3px 6px', height: '100%', @@ -408,11 +369,10 @@ export default function QueryToolDataGrid({columns, rows, totalRowCount, dataCha return ( - ({ sql: { @@ -276,7 +277,7 @@ export default function Query() { eventBus.registerListener(QUERY_TOOL_EVENTS.LOAD_FILE, (fileName)=>{ queryToolCtx.api.post(url_for('sqleditor.load_file'), { 'file_name': decodeURI(fileName), - }).then((res)=>{ + }, {transformResponse: [(data) => { return data; }]}).then((res)=>{ editor.current.setValue(res.data); //Check the file content for Trojan Source checkTrojanSource(res.data); @@ -284,7 +285,7 @@ export default function Query() { eventBus.fireEvent(QUERY_TOOL_EVENTS.LOAD_FILE_DONE, fileName, true); }).catch((err)=>{ eventBus.fireEvent(QUERY_TOOL_EVENTS.LOAD_FILE_DONE, null, false); - eventBus.fireEvent(QUERY_TOOL_EVENTS.HANDLE_API_ERROR, err); + Notifier.error(parseApiError(err)); }); }); diff --git a/web/pgadmin/tools/storage_manager/__init__.py b/web/pgadmin/tools/storage_manager/__init__.py deleted file mode 100644 index 7850f6f95..000000000 --- a/web/pgadmin/tools/storage_manager/__init__.py +++ /dev/null @@ -1,51 +0,0 @@ -########################################################################## -# -# pgAdmin 4 - PostgreSQL Tools -# -# Copyright (C) 2013 - 2022, The pgAdmin Development Team -# This software is released under the PostgreSQL Licence -# -########################################################################## - -"""A blueprint module implementing the storage manager functionality""" - -from flask import url_for, Response, render_template -from flask_babel import gettext as _ -from flask_security import login_required - -from pgadmin.utils import PgAdminModule -from pgadmin.utils.ajax import bad_request -from pgadmin.utils.constants import MIMETYPE_APP_JS - -MODULE_NAME = 'storage_manager' - - -class StorageManagerModule(PgAdminModule): - """ - class StorageManagerModule(PgAdminModule) - - A module class for manipulating file operation which is derived from - PgAdminModule. - """ - - LABEL = _('Storage Manager') - - -blueprint = StorageManagerModule(MODULE_NAME, __name__) - - -@blueprint.route("/") -@login_required -def index(): - return bad_request(errormsg=_("This URL cannot be called directly.")) - - -@blueprint.route("/js/storage_manager.js") -@login_required -def script(): - """render the import/export javascript file""" - return Response( - response=render_template("storage_manager/js/storage_manager.js", _=_), - status=200, - mimetype=MIMETYPE_APP_JS - ) diff --git a/web/pgadmin/tools/storage_manager/static/js/storage_manager.js b/web/pgadmin/tools/storage_manager/static/js/storage_manager.js deleted file mode 100644 index cba26d288..000000000 --- a/web/pgadmin/tools/storage_manager/static/js/storage_manager.js +++ /dev/null @@ -1,93 +0,0 @@ -///////////////////////////////////////////////////////////// -// -// pgAdmin 4 - PostgreSQL Tools -// -// Copyright (C) 2013 - 2022, The pgAdmin Development Team -// This software is released under the PostgreSQL Licence -// -////////////////////////////////////////////////////////////// -import { set_last_traversed_dir, getTransId } from '../../../../misc/file_manager/static/js/helpers'; - -define([ - 'sources/gettext', 'sources/url_for', 'jquery', 'underscore', 'pgadmin.alertifyjs', - 'sources/pgadmin', 'pgadmin.browser', 'sources/csrf', 'pgadmin.file_manager', -], function ( - gettext, url_for, $, _, alertify, pgAdmin, pgBrowser, csrfToken -) { - - pgAdmin = pgAdmin || window.pgAdmin || {}; - var isServerMode = (function() { return pgAdmin.server_mode == 'True'; })(); - - var pgTools = pgAdmin.Tools = pgAdmin.Tools || {}; - - if(!isServerMode) { - return; - } - - // Return back, this has been called more than once - if (pgAdmin.Tools.storage_manager) - return pgAdmin.Tools.storage_manager; - - pgTools.storage_manager = { - init: function () { - // We do not want to initialize the module multiple times. - if (this.initialized) - return; - - this.initialized = true; - csrfToken.setPGCSRFToken(pgAdmin.csrf_token_header, pgAdmin.csrf_token); - - var storage_manager = this.callback_storage_manager.bind(this); - - pgBrowser.Events.on( - 'pgadmin:tools:storage_manager', storage_manager - ); - - // Define the nodes on which the menus to be appear - var menus = [{ - name: 'storage_manager', - module: this, - applies: ['tools'], - callback: 'callback_storage_manager', - priority: 11, - label: gettext('Storage Manager...'), - enable: true, - }]; - - pgBrowser.add_menus(menus); - }, - - /* - Open the dialog for the storage functionality - */ - callback_storage_manager: function (path) { - - var params = { - supported_types: ['sql', 'csv', 'json', '*'], - dialog_type: 'storage_dialog', - dialog_title: 'Storage Manager', - btn_primary: undefined, - }; - - if (!_.isUndefined(path) && !_.isNull(path) && !_.isEmpty(path)) { - - var transId = getTransId(JSON.stringify(params)); - var t_res; - if (transId.readyState == 4) { - t_res = JSON.parse(transId.responseText); - } - var trans_id = _.isUndefined(t_res) ? 0 : t_res.data.fileTransId; - - set_last_traversed_dir({'path': path}, trans_id); - pgAdmin.FileManager.init(); - pgAdmin.FileManager.show_dialog(params); - } - else { - pgAdmin.FileManager.init(); - pgAdmin.FileManager.show_dialog(params); - } - }, - }; - - return pgAdmin.Tools.storage_manager; -}); diff --git a/web/regression/javascript/SchemaView/SchemaView.spec.js b/web/regression/javascript/SchemaView/SchemaView.spec.js index 36757abba..aea2c1d40 100644 --- a/web/regression/javascript/SchemaView/SchemaView.spec.js +++ b/web/regression/javascript/SchemaView/SchemaView.spec.js @@ -15,7 +15,6 @@ import {TestSchema, TestSchemaAllTypes} from './TestSchema.ui'; import pgAdmin from 'sources/pgadmin'; import {messages} from '../fake_messages'; import SchemaView from '../../../pgadmin/static/js/SchemaView'; -import * as legacyConnector from 'sources/helpers/legacyConnector'; import Notify from '../../../pgadmin/static/js/helpers/Notifier'; import Theme from '../../../pgadmin/static/js/Theme'; @@ -191,18 +190,17 @@ describe('SchemaView', ()=>{ simulateValidData(); /* Press OK */ - let confirmSpy = spyOn(legacyConnector, 'confirmDeleteRow').and.callFake((yesFn)=>{ - yesFn(); - }); + let confirmSpy = spyOn(Notify, 'confirm').and.callThrough(); ctrl.find('DataGridView').find('PgIconButton[data-test="delete-row"]').at(0).find('button').simulate('click'); - expect(confirmSpy.calls.argsFor(0)[2]).toBe('Custom delete title'); - expect(confirmSpy.calls.argsFor(0)[3]).toBe('Custom delete message'); + confirmSpy.calls.argsFor(0)[2](); + expect(confirmSpy.calls.argsFor(0)[0]).toBe('Custom delete title'); + expect(confirmSpy.calls.argsFor(0)[1]).toBe('Custom delete message'); /* Press Cancel */ - spyOn(legacyConnector, 'confirmDeleteRow').and.callFake((yesFn, cancelFn)=>{ - cancelFn(); - }); + confirmSpy.calls.reset(); ctrl.find('DataGridView').find('PgIconButton[data-test="delete-row"]').at(0).find('button').simulate('click'); + confirmSpy.calls.argsFor(0)[3](); + setTimeout(()=>{ ctrlUpdate(done); }, 0); @@ -297,7 +295,7 @@ describe('SchemaView', ()=>{ }, 0); }); - let onRestAction = (done, data)=> { + let onResetAction = (done, data)=> { ctrl.update(); expect(ctrl.find('DefaultButton[data-test="Reset"]').prop('disabled')).toBeTrue(); expect(ctrl.find('PrimaryButton[data-test="Save"]').prop('disabled')).toBeTrue(); @@ -316,7 +314,7 @@ describe('SchemaView', ()=>{ /* Press OK */ confirmSpy.calls.argsFor(0)[2](); setTimeout(()=>{ - onRestAction(done, { id: undefined, field1: null, field2: null, fieldcoll: null }); + onResetAction(done, { id: undefined, field1: null, field2: null, fieldcoll: null }); }, 0); }, 0); }); @@ -390,7 +388,9 @@ describe('SchemaView', ()=>{ ctrl.find('MappedCellControl[id="field5"]').at(2).find('input').simulate('change', {target: {value: 'rval53'}}); /* Remove the 1st row */ + let confirmSpy = spyOn(Notify, 'confirm').and.callThrough(); ctrl.find('DataTableRow').find('PgIconButton[data-test="delete-row"]').at(0).find('button').simulate('click'); + confirmSpy.calls.argsFor(0)[2](); /* Edit the 2nd row which is first now*/ ctrl.find('MappedCellControl[id="field5"]').at(0).find('input').simulate('change', {target: {value: 'rvalnew'}}); @@ -403,11 +403,6 @@ describe('SchemaView', ()=>{ mode: 'edit', } }); - - /* Press OK */ - spyOn(legacyConnector, 'confirmDeleteRow').and.callFake((yesFn)=>{ - yesFn(); - }); }); it('init', (done)=>{ setTimeout(()=>{ @@ -463,9 +458,9 @@ describe('SchemaView', ()=>{ let confirmSpy = spyOn(Notify, 'confirm').and.callThrough(); ctrl.find('DefaultButton[data-test="Reset"]').simulate('click'); /* Press OK */ - confirmSpy.calls.argsFor(0)[2](); + confirmSpy.calls.mostRecent().args[2](); setTimeout(()=>{ - onRestAction(done, {}); + onResetAction(done, {}); }, 0); }, 0); }); diff --git a/web/regression/javascript/components/FormComponents.spec.js b/web/regression/javascript/components/FormComponents.spec.js index be70cb272..635e09756 100644 --- a/web/regression/javascript/components/FormComponents.spec.js +++ b/web/regression/javascript/components/FormComponents.spec.js @@ -28,10 +28,10 @@ import {FormInputText, FormInputFileSelect, FormInputSQL, FormInputColor, FormFooterMessage, MESSAGE_TYPE} from '../../../pgadmin/static/js/components/FormComponents'; -import * as legacyConnector from '../../../pgadmin/static/js/helpers/legacyConnector'; import CodeMirror from '../../../pgadmin/static/js/components/CodeMirror'; import { ToggleButton } from '@material-ui/lab'; import { DefaultButton, PrimaryButton } from '../../../pgadmin/static/js/components/Buttons'; +import * as showFileManager from '../../../pgadmin/static/js/helpers/showFileManager'; /* MUI Components need to be wrapped in Theme for theme vars */ describe('FormComponents', ()=>{ @@ -118,7 +118,7 @@ describe('FormComponents', ()=>{ let ThemedFormInputFileSelect = withTheme(FormInputFileSelect), ctrl; beforeEach(()=>{ - spyOn(legacyConnector, 'showFileDialog').and.callFake((controlProps, onFileSelect)=>{ + spyOn(showFileManager, 'showFileManager').and.callFake((controlProps, onFileSelect)=>{ onFileSelect('selected/file'); }); ctrl = mount( diff --git a/web/regression/javascript/erd/ui_components/body_widget_spec.js b/web/regression/javascript/erd/ui_components/body_widget_spec.js index 74afced32..04f9fa13c 100644 --- a/web/regression/javascript/erd/ui_components/body_widget_spec.js +++ b/web/regression/javascript/erd/ui_components/body_widget_spec.js @@ -38,12 +38,11 @@ let pgAdmin = { app_version_int: 1234, }, }, - FileManager: { - init: jasmine.createSpy(), - show_dialog: jasmine.createSpy(), - }, Tools: { SQLEditor: {}, + FileManager: { + show: jasmine.createSpy(), + }, } }; @@ -360,7 +359,7 @@ describe('ERD BodyWidget', ()=>{ it('onLoadDiagram', ()=>{ bodyInstance.onLoadDiagram(); - expect(pgAdmin.FileManager.show_dialog).toHaveBeenCalled(); + expect(pgAdmin.Tools.FileManager.show).toHaveBeenCalled(); }); it('openFile', (done)=>{ @@ -389,9 +388,10 @@ describe('ERD BodyWidget', ()=>{ done(); }); + pgAdmin.Tools.FileManager.show.calls.reset(); bodyInstance.onSaveDiagram(true); - expect(pgAdmin.FileManager.show_dialog).toHaveBeenCalledWith({ - 'supported_types': ['pgerd'], + expect(pgAdmin.Tools.FileManager.show.calls.argsFor(0)[0]).toEqual({ + 'supported_types': ['*','pgerd'], 'dialog_type': 'create_file', 'dialog_title': 'Save File', 'btn_primary': 'Save', diff --git a/web/regression/javascript/fake_endpoints.js b/web/regression/javascript/fake_endpoints.js index fd5ec175f..79686fe55 100644 --- a/web/regression/javascript/fake_endpoints.js +++ b/web/regression/javascript/fake_endpoints.js @@ -28,5 +28,13 @@ define(function () { 'erd.sql': '/erd/sql////', 'erd.prequisite': '/erd/prequisite////', 'erd.tables': '/erd/tables////', + 'file_manager.init': '/file_manager/init', + 'file_manager.filemanager': '/file_manager/init', + 'file_manager.index': '/file_manager/', + 'file_manager.delete_trans_id': '/file_manager/delete_trans_id/', + 'file_manager.save_last_dir': '/file_manager/save_last_dir/', + 'file_manager.save_file_dialog_view': '/file_manager/save_file_dialog_view/', + 'file_manager.save_show_hidden_file_option': '/file_manager/save_show_hidden_file_option/', + 'settings.save_file_format_setting': '/settings/save_file_format_setting/', }; }); diff --git a/web/regression/javascript/file_manager/FileManager.spec.js b/web/regression/javascript/file_manager/FileManager.spec.js new file mode 100644 index 000000000..c41136796 --- /dev/null +++ b/web/regression/javascript/file_manager/FileManager.spec.js @@ -0,0 +1,324 @@ +///////////////////////////////////////////////////////////// +// +// pgAdmin 4 - PostgreSQL Tools +// +// Copyright (C) 2013 - 2022, The pgAdmin Development Team +// This software is released under the PostgreSQL Licence +// +////////////////////////////////////////////////////////////// + +import jasmineEnzyme from 'jasmine-enzyme'; +import React from 'react'; +import '../helper/enzyme.helper'; +import { createMount } from '@material-ui/core/test-utils'; +import Theme from '../../../pgadmin/static/js/Theme'; +import FileManager, { FileManagerUtils, getComparator } from '../../../pgadmin/misc/file_manager/static/js/components/FileManager'; +import MockAdapter from 'axios-mock-adapter'; +import axios from 'axios/index'; +import getApiInstance from '../../../pgadmin/static/js/api_instance'; +import * as pgUtils from '../../../pgadmin/static/js/utils'; + +const files = [ + { + 'Filename': 'file1.sql', + 'Path': '/home/file1', + 'file_type': 'sql', + 'Protected': 0, + 'Properties': { + 'Date Created': 'Fri Oct 22 16:59:24 2021', + 'Date Modified': 'Tue Oct 12 14:08:00 2021', + 'Size': '1.4 MB' + } + }, + { + 'Filename': 'folder1', + 'Path': '/home/folder1', + 'file_type': 'dir', + 'Protected': 0, + 'Properties': { + 'Date Created': 'Fri Oct 22 16:59:24 2021', + 'Date Modified': 'Tue Oct 12 14:08:00 2021', + 'Size': '1.4 MB' + } + } +]; + +const transId = 140391; +const configData = { + 'transId': transId, + 'options': { + 'culture': 'en', + 'lang': 'py', + 'defaultViewMode':'list', + 'autoload': true, + 'showFullPath': false, + 'dialog_type': 'select_folder', + 'show_hidden_files': false, + 'fileRoot': '/home/current', + 'capabilities': [ + 'select_folder', 'select_file', 'download', + 'rename', 'delete', 'upload', 'create' + ], + 'allowed_file_types': [ + '*', + 'sql', + 'backup' + ], + 'platform_type': 'darwin', + 'show_volumes': true, + 'homedir': '/home/', + 'last_selected_format': '*' + }, + 'security': { + 'uploadPolicy': '', + 'uploadRestrictions': [ + '*', + 'sql', + 'backup' + ] + }, + 'upload': { + 'multiple': true, + 'number': 20, + 'fileSizeLimit': 50, + 'imagesOnly': false + } +}; + +const params={ + dialog_type: 'select_file', +}; + +describe('FileManger', ()=>{ + let mount; + let networkMock; + + /* Use createMount so that material ui components gets the required context */ + /* https://material-ui.com/guides/testing/#api */ + beforeAll(()=>{ + mount = createMount(); + networkMock = new MockAdapter(axios); + networkMock.onPost('/file_manager/init').reply(200, {'data': configData}); + networkMock.onPost(`/file_manager/filemanager/${transId}/`).reply(200, {data: {result: files}}); + networkMock.onDelete(`/file_manager/delete_trans_id/${transId}`).reply(200, {}); + }); + + afterAll(() => { + mount.cleanUp(); + networkMock.restore(); + }); + + beforeEach(()=>{ + jasmineEnzyme(); + }); + + describe('FileManger', ()=>{ + let closeModal=jasmine.createSpy('closeModal'), + onOK=jasmine.createSpy('onOK'), + onCancel=jasmine.createSpy('onCancel'), + ctrlMount = (props)=>{ + return mount( + + ); + }; + + it('init', (done)=>{ + let ctrl = ctrlMount({}); + setTimeout(()=>{ + ctrl.update(); + expect(ctrl.find('ListView').length).toBe(1); + expect(ctrl.find('GridView').length).toBe(0); + expect(ctrl.find('InputText[data-label="file-path"]').prop('value')).toBe('/home/current'); + ctrl?.unmount(); + let config = {...configData}; + config.options.defaultViewMode = 'grid'; + networkMock.onPost('/file_manager/init').reply(200, {'data': config}); + ctrl = ctrlMount({}); + setTimeout(()=>{ + ctrl.update(); + expect(ctrl.find('ListView').length).toBe(0); + expect(ctrl.find('GridView').length).toBe(1); + ctrl?.unmount(); + done(); + }, 0); + }, 500); + }); + + describe('getComparator', ()=>{ + it('Filename', ()=>{ + expect(getComparator({columnKey: 'Filename', direction: 'ASC'})({Filename:'a'}, {Filename:'b'})).toBe(-1); + expect(getComparator({columnKey: 'Filename', direction: 'DESC'})({Filename:'a'}, {Filename:'b'})).toBe(1); + expect(getComparator({columnKey: 'Filename', direction: 'ASC'})({Filename:'a'}, {Filename:'A'})).toBe(-1); + }); + + it('Properties.DateModified', ()=>{ + expect(getComparator({columnKey: 'Properties.DateModified', direction: 'ASC'})( + {Properties:{'Date Modified':'Tue Feb 25 11:36:28 2020'}}, {Properties:{'Date Modified':'Tue Feb 26 11:36:28 2020'}}) + ).toBe(-1); + expect(getComparator({columnKey: 'Properties.DateModified', direction: 'DESC'})( + {Properties:{'Date Modified':'Tue Feb 25 11:36:28 2020'}}, {Properties:{'Date Modified':'Tue Feb 26 11:36:28 2020'}}) + ).toBe(1); + expect(getComparator({columnKey: 'Properties.DateModified', direction: 'ASC'})( + {Properties:{'Date Modified':'Tue Feb 25 11:36:28 2020'}}, {Properties:{'Date Modified':'Tue Feb 25 11:36:28 2020'}}) + ).toBe(0); + }); + + it('Properties.Size', ()=>{ + expect(getComparator({columnKey: 'Properties.Size', direction: 'ASC'})( + {Properties:{'Size':'1 KB'}}, {Properties:{'Size':'1 MB'}}) + ).toBe(-1); + expect(getComparator({columnKey: 'Properties.Size', direction: 'DESC'})( + {Properties:{'Size':'1 MB'}}, {Properties:{'Size':'1 GB'}}) + ).toBe(1); + expect(getComparator({columnKey: 'Properties.Size', direction: 'ASC'})( + {Properties:{'Size':'1 MB'}}, {Properties:{'Size':'1 MB'}}) + ).toBe(0); + }); + }); + }); +}); + +describe('FileManagerUtils', ()=>{ + let api, fmObj, networkMock; + beforeEach(()=>{ + networkMock = new MockAdapter(axios); + networkMock.onDelete(`/file_manager/delete_trans_id/${transId}`).reply(200, {}); + networkMock.onPost(`/file_manager/filemanager/${transId}/`).reply((config)=>{ + let retVal = {}; + let apiData = JSON.parse(config.data); + let headers = {}; + if(apiData.mode == 'addfolder') { + retVal = {data: {result: { + Name: apiData.name, + Path: '/home/'+apiData.name, + 'Date Modified': 'Tue Feb 25 11:36:28 2020', + }}}; + } else if(apiData.mode == 'rename') { + retVal = {data: {result: { + 'New Path': '/home/'+apiData.new, + 'New Name': apiData.new, + }}}; + } else if(apiData.mode == 'download') { + retVal = 'blobdata'; + headers = {filename: 'newfile1'}; + } else if(apiData.mode == 'is_file_exist') { + retVal = {data: {result: {Code: 1}}}; + } + return [200, retVal, headers]; + }); + + api = getApiInstance(); + fmObj = new FileManagerUtils(api, params); + fmObj.config = configData; + }); + + afterEach(()=>{ + networkMock.restore(); + }); + + it('showHiddenFiles', ()=>{ + expect(fmObj.showHiddenFiles).toBe(false); + networkMock.onPut(`/file_manager/save_show_hidden_file_option/${transId}`).reply(200, {}); + fmObj.showHiddenFiles = true; + expect(fmObj.config.options?.show_hidden_files).toBe(true); + }); + + it('setLastVisitedDir', async ()=>{ + let calledPath = null; + networkMock.onPost(`/file_manager/save_last_dir/${transId}`).reply((config)=>{ + calledPath = JSON.parse(config.data).path; + return [200, {}]; + }); + await fmObj.setLastVisitedDir('/home/xyz'); + expect(calledPath).toBe('/home/xyz'); + }); + + it('setDialogView', async ()=>{ + networkMock.onPost(`/file_manager/save_file_dialog_view/${transId}`).reply(200, {}); + await fmObj.setDialogView('grid'); + expect(fmObj.config.options.defaultViewMode).toBe('grid'); + }); + + it('setFileType', async ()=>{ + networkMock.onPost('/settings/save_file_format_setting/').reply(200, {}); + await fmObj.setFileType('pgerd'); + expect(fmObj.config.options.last_selected_format).toBe('pgerd'); + }); + + it('join', ()=>{ + expect(fmObj.join('/dir1/dir2', 'file1')).toBe('/dir1/dir2/file1'); + expect(fmObj.join('/dir1/dir2/', 'file1')).toBe('/dir1/dir2/file1'); + }); + + it('addFolder', async ()=>{ + let res = await fmObj.addFolder({Filename: 'newfolder'}); + expect(res).toEqual({ + Filename: 'newfolder', + Path: '/home/newfolder', + file_type: 'dir', + Properties: { + 'Date Modified': 'Tue Feb 25 11:36:28 2020', + } + }); + }); + + it('rename', async ()=>{ + let row = {Filename: 'newfolder1', Path: '/home/newfolder'}; + let res = await fmObj.renameItem(row); + expect(res).toEqual({ + Filename: 'newfolder1', + Path: '/home/newfolder1', + }); + }); + + it('deleteItem', async ()=>{ + let row = {Filename: 'newfolder', Path: '/home/newfolder'}; + let path = await fmObj.deleteItem(row); + expect(path).toBe('/home/newfolder'); + + path = await fmObj.deleteItem(row, 'file1'); + expect(path).toBe('/home/newfolder/file1'); + }); + + it('checkPermission', async ()=>{ + networkMock.reset(); + networkMock.onPost(`/file_manager/filemanager/${transId}/`).reply(200, { + data: { + result: { + Code: 1, + } + } + }); + let res = await fmObj.checkPermission('/home/newfolder'); + expect(res).toEqual(null); + + networkMock.onPost(`/file_manager/filemanager/${transId}/`).reply(200, { + data: { + result: { + Code: 0, + Error: 'file error' + } + } + }); + res = await fmObj.checkPermission('/home/newfolder'); + expect(res).toEqual('file error'); + }); + + it('isFileExists', async ()=>{ + let res = await fmObj.isFileExists('/home/newfolder', 'newfile1'); + expect(res).toBe(true); + }); + + it('downloadFile', async ()=>{ + spyOn(pgUtils, 'downloadBlob'); + let row = {Filename: 'newfile1', Path: '/home/newfile1'}; + await fmObj.downloadFile(row); + expect(pgUtils.downloadBlob).toHaveBeenCalledWith('blobdata', 'newfile1'); + }); +}); diff --git a/web/regression/javascript/file_manager/GridView.spec.js b/web/regression/javascript/file_manager/GridView.spec.js new file mode 100644 index 000000000..b2bb7483e --- /dev/null +++ b/web/regression/javascript/file_manager/GridView.spec.js @@ -0,0 +1,62 @@ +///////////////////////////////////////////////////////////// +// +// pgAdmin 4 - PostgreSQL Tools +// +// Copyright (C) 2013 - 2022, The pgAdmin Development Team +// This software is released under the PostgreSQL Licence +// +////////////////////////////////////////////////////////////// + +import jasmineEnzyme from 'jasmine-enzyme'; +import React from 'react'; +import '../helper/enzyme.helper'; +import { createMount } from '@material-ui/core/test-utils'; +import Theme from '../../../pgadmin/static/js/Theme'; +import { ItemView } from '../../../pgadmin/misc/file_manager/static/js/components/GridView'; + +describe('GridView', ()=>{ + let mount; + + /* Use createMount so that material ui components gets the required context */ + /* https://material-ui.com/guides/testing/#api */ + beforeAll(()=>{ + mount = createMount(); + }); + + afterAll(() => { + mount.cleanUp(); + }); + + beforeEach(()=>{ + jasmineEnzyme(); + }); + + describe('ItemView', ()=>{ + let row = {'Filename': 'test.sql', 'Size': '1KB', 'file_type': 'dir'}, + ctrlMount = (props)=>{ + return mount( + + ); + }; + + it('keydown Escape', (done)=>{ + const onEditComplete = jasmine.createSpy('onEditComplete'); + let ctrl = ctrlMount({ + onEditComplete: onEditComplete, + }); + setTimeout(()=>{ + ctrl.update(); + ctrl.find('div[data-test="filename-div"]').simulate('keydown', { code: 'Escape'}); + setTimeout(()=>{ + expect(onEditComplete).toHaveBeenCalled(); + done(); + }); + }, 0); + }); + }); +}); diff --git a/web/regression/javascript/file_manager/ListView.spec.js b/web/regression/javascript/file_manager/ListView.spec.js new file mode 100644 index 000000000..8036579ae --- /dev/null +++ b/web/regression/javascript/file_manager/ListView.spec.js @@ -0,0 +1,110 @@ +///////////////////////////////////////////////////////////// +// +// pgAdmin 4 - PostgreSQL Tools +// +// Copyright (C) 2013 - 2022, The pgAdmin Development Team +// This software is released under the PostgreSQL Licence +// +////////////////////////////////////////////////////////////// + +import jasmineEnzyme from 'jasmine-enzyme'; +import React from 'react'; +import '../helper/enzyme.helper'; +import { createMount } from '@material-ui/core/test-utils'; +import Theme from '../../../pgadmin/static/js/Theme'; +import { CustomRow, FileNameEditor, GridContextUtils } from '../../../pgadmin/misc/file_manager/static/js/components/ListView'; + +describe('ListView', ()=>{ + let mount; + + /* Use createMount so that material ui components gets the required context */ + /* https://material-ui.com/guides/testing/#api */ + beforeAll(()=>{ + mount = createMount(); + }); + + afterAll(() => { + mount.cleanUp(); + }); + + beforeEach(()=>{ + jasmineEnzyme(); + }); + + describe('FileNameEditor', ()=>{ + let row = {'Filename': 'test.sql', 'Size': '1KB'}, + column = { + key: 'Filename' + }, + ctrlMount = (props)=>{ + return mount( + + ); + }; + + it('init', (done)=>{ + let ctrl = ctrlMount({ + onRowChange: ()=>{/* test func */}, + onClose: ()=>{/* test func */}, + }); + setTimeout(()=>{ + ctrl.update(); + expect(ctrl.find('input').props()).toEqual(jasmine.objectContaining({value: 'test.sql'})); + done(); + }, 0); + }); + + it('keydown Tab', (done)=>{ + let onCloseSpy = jasmine.createSpy('onClose'); + let ctrl = ctrlMount({ + onRowChange: ()=>{/* test func */}, + onClose: onCloseSpy, + }); + setTimeout(()=>{ + ctrl.update(); + expect(ctrl.find('input').props()).toEqual(jasmine.objectContaining({value: 'test.sql'})); + ctrl.find('input').simulate('keydown', { code: 'Tab'}); + setTimeout(()=>{ + expect(onCloseSpy).toHaveBeenCalled(); + done(); + }); + }, 0); + }); + }); + + describe('CustomRow', ()=>{ + let row = {'Filename': 'test.sql', 'Size': '1KB'}, + ctrlMount = (onItemSelect, onItemEnter)=>{ + return mount( + + + + ); + }; + + it('init', (done)=>{ + let onItemSelect = jasmine.createSpy('onItemSelect'); + let onItemEnter = jasmine.createSpy('onItemEnter'); + let ctrl = ctrlMount(onItemSelect, onItemEnter); + setTimeout(()=>{ + ctrl.update(); + ctrl.find('div[data-test="test-div"]').simulate('keydown', { code: 'Enter'}); + setTimeout(()=>{ + ctrl.update(); + expect(onItemEnter).toHaveBeenCalled(); + ctrl?.unmount(); + done(); + }, 0); + }, 0); + }); + }); +}); diff --git a/web/regression/javascript/file_manager/Uploader.spec.js b/web/regression/javascript/file_manager/Uploader.spec.js new file mode 100644 index 000000000..8c094c237 --- /dev/null +++ b/web/regression/javascript/file_manager/Uploader.spec.js @@ -0,0 +1,233 @@ +///////////////////////////////////////////////////////////// +// +// pgAdmin 4 - PostgreSQL Tools +// +// Copyright (C) 2013 - 2022, The pgAdmin Development Team +// This software is released under the PostgreSQL Licence +// +////////////////////////////////////////////////////////////// + +import jasmineEnzyme from 'jasmine-enzyme'; +import React from 'react'; +import '../helper/enzyme.helper'; +import { createMount } from '@material-ui/core/test-utils'; +import Theme from '../../../pgadmin/static/js/Theme'; +import Uploader, { filesReducer, getFileSize, UploadedFile } from '../../../pgadmin/misc/file_manager/static/js/components/Uploader'; +import { MESSAGE_TYPE } from '../../../pgadmin/static/js/components/FormComponents'; + +describe('GridView', ()=>{ + let mount; + + /* Use createMount so that material ui components gets the required context */ + /* https://material-ui.com/guides/testing/#api */ + beforeAll(()=>{ + mount = createMount(); + }); + + afterAll(() => { + mount.cleanUp(); + }); + + beforeEach(()=>{ + jasmineEnzyme(); + }); + + describe('Uploader', ()=>{ + let fmUtilsObj = jasmine.createSpyObj('fmUtilsObj', ['uploadItem', 'deleteItem'], ['currPath']); + let onClose = jasmine.createSpy('onClose'); + let ctrlMount = (props)=>{ + return mount( + + ); + }; + + it('init', (done)=>{ + let ctrl = ctrlMount(); + setTimeout(()=>{ + ctrl.update(); + done(); + }, 0); + }); + + describe('filesReducer', ()=>{ + let state; + + beforeEach(()=>{ + state = [ + { + id: 1, + file: 'file1', + progress: 0, + started: false, + failed: false, + done: false, + } + ]; + }); + + it('add', ()=>{ + let newState = filesReducer(state, { + type: 'add', + files: ['new1'], + }); + expect(newState.length).toBe(2); + expect(newState[0]).toEqual(jasmine.objectContaining({ + file: 'new1', + progress: 0, + started: false, + failed: false, + done: false, + })); + }); + + + it('started', ()=>{ + let newState = filesReducer(state, { + type: 'started', + id: 1, + }); + expect(newState[0]).toEqual(jasmine.objectContaining({ + file: 'file1', + progress: 0, + started: true, + failed: false, + done: false, + })); + }); + + it('started', ()=>{ + let newState = filesReducer(state, { + type: 'progress', + id: 1, + value: 14, + }); + expect(newState[0]).toEqual(jasmine.objectContaining({ + file: 'file1', + progress: 14, + started: false, + failed: false, + done: false, + })); + }); + + it('failed', ()=>{ + let newState = filesReducer(state, { + type: 'failed', + id: 1, + }); + expect(newState[0]).toEqual(jasmine.objectContaining({ + file: 'file1', + progress: 0, + started: false, + failed: true, + done: false, + })); + }); + + it('done', ()=>{ + let newState = filesReducer(state, { + type: 'done', + id: 1, + }); + expect(newState[0]).toEqual(jasmine.objectContaining({ + file: 'file1', + progress: 0, + started: false, + failed: false, + done: true, + })); + }); + + it('remove', ()=>{ + let newState = filesReducer(state, { + type: 'remove', + id: 1, + }); + expect(newState.length).toBe(0); + }); + }); + + it('getFileSize', ()=>{ + expect(getFileSize(1024)).toBe('1 KB'); + }); + + describe('UploadedFile', ()=>{ + let upCtrlMount = (props)=>{ + return mount( + {/*dummy*/}} + onClose={onClose} + {...props} + /> + ); + }; + + it('uploading', (done)=>{ + let ctrl = upCtrlMount({upfile: { + file: { + name: 'file1', + size: '1KB', + }, + done: false, + failed: false, + progress: 14, + }}); + + setTimeout(()=>{ + ctrl.update(); + expect(ctrl.find('FormFooterMessage').props()).toEqual(jasmine.objectContaining({ + type: MESSAGE_TYPE.INFO, + message: 'Uploading... 14%', + })); + done(); + }, 0); + }); + + it('done', (done)=>{ + let ctrl = upCtrlMount({upfile: { + file: { + name: 'file1', + size: '1KB', + }, + done: true, + failed: false, + progress: 14, + }}); + + setTimeout(()=>{ + ctrl.update(); + expect(ctrl.find('FormFooterMessage').props()).toEqual(jasmine.objectContaining({ + type: MESSAGE_TYPE.SUCCESS, + message: 'Uploaded!', + })); + done(); + }, 0); + }); + + it('failed', (done)=>{ + let ctrl = upCtrlMount({upfile: { + file: { + name: 'file1', + size: '1KB', + }, + done: false, + failed: true, + progress: 14, + }}); + + setTimeout(()=>{ + ctrl.update(); + expect(ctrl.find('FormFooterMessage').props()).toEqual(jasmine.objectContaining({ + type: MESSAGE_TYPE.ERROR, + message: 'Failed!', + })); + done(); + }, 0); + }); + }); + }); +}); diff --git a/web/regression/javascript/file_manager/file_manager_specs.js b/web/regression/javascript/file_manager/file_manager_specs.js deleted file mode 100644 index fd860817e..000000000 --- a/web/regression/javascript/file_manager/file_manager_specs.js +++ /dev/null @@ -1,128 +0,0 @@ -///////////////////////////////////////////////////////////// -// -// pgAdmin 4 - PostgreSQL Tools -// -// Copyright (C) 2013 - 2022, The pgAdmin Development Team -// This software is released under the PostgreSQL Licence -// -////////////////////////////////////////////////////////////// - -import pgAdmin from 'sources/pgadmin'; -import Alertify from 'pgadmin.alertifyjs'; -import '../../../pgadmin/misc/file_manager/static/js/file_manager'; -import '../../../pgadmin/misc/file_manager/static/js/select_dialogue.js'; - - -describe('fileSelectDialog', function () { - - let params; - let calcWidth = (passed_width)=>{ - let iw = window.innerWidth; - if (iw > passed_width){ - return passed_width; - } else { - if (iw > pgAdmin.Browser.stdW.lg) - return pgAdmin.Browser.stdW.lg; - else if (iw > pgAdmin.Browser.stdW.md) - return pgAdmin.Browser.stdW.md; - else if (iw > pgAdmin.Browser.stdW.sm) - return pgAdmin.Browser.stdW.sm; - else - // if available screen resolution is still - // less then return the width value as it - return iw; - } - }; - - let calcHeight = (passed_height)=>{ - // We are excluding sm as it is too small for dialog - let ih = window.innerHeight; - if (ih > passed_height){ - return passed_height; - }else{ - if (ih > pgAdmin.Browser.stdH.lg) - return pgAdmin.Browser.stdH.lg; - else if (ih > pgAdmin.Browser.stdH.md) - return pgAdmin.Browser.stdH.md; - else - // if available screen resolution is still - // less then return the height value as it - return ih; - } - }; - - beforeAll(() => { - pgAdmin.Browser = { - stdW: { - sm: 500, - md: 700, - lg: 900, - default: 500, - calc: (passed_width) => { - calcWidth(passed_width); - }, - }, - stdH: { - sm: 200, - md: 400, - lg: 550, - default: 550, - calc: (passed_height) => { - calcHeight(passed_height); - }, - }, - }; - }); - - describe('When dialog is called for', () => { - it('Select file', function() { - params = { - 'dialog_title': 'Select file', - 'dialog_type': 'select_file', - }; - - spyOn(Alertify, 'fileSelectionDlg').and.callFake(function() { - this.resizeTo = function() {/*This is intentional (SonarQube)*/}; - return this; - }); - - pgAdmin.FileManager.show_dialog(params); - - expect(Alertify.fileSelectionDlg).toHaveBeenCalled(); - }); - - it('create file', function() { - params = { - 'dialog_title': 'Create file', - 'dialog_type': 'create_file', - }; - - spyOn(Alertify, 'createModeDlg').and.callFake(function() { - this.resizeTo = function() {/*This is intentional (SonarQube)*/}; - return this; - }); - - pgAdmin.FileManager.show_dialog(params); - - expect(Alertify.createModeDlg).toHaveBeenCalled(); - }); - }); - - describe('When dialog is called for storage file', () => { - it('Storage file dialog', function() { - params = { - 'dialog_title': 'Storage Manager', - 'dialog_type': 'storage_dialog', - }; - - spyOn(Alertify, 'fileStorageDlg').and.callFake(function() { - this.resizeTo = function() {/*This is intentional (SonarQube)*/}; - return this; - }); - - pgAdmin.FileManager.show_dialog(params); - - expect(Alertify.fileStorageDlg).toHaveBeenCalled(); - }); - }); -}); diff --git a/web/webpack.config.js b/web/webpack.config.js index 210627608..8873198a4 100644 --- a/web/webpack.config.js +++ b/web/webpack.config.js @@ -381,7 +381,6 @@ module.exports = [{ schema_diff: './pgadmin/tools/schema_diff/static/js/schema_diff_hook.js', erd_tool: './pgadmin/tools/erd/static/js/erd_tool_hook.js', psql_tool: './pgadmin/tools/psql/static/js/index.js', - file_utils: './pgadmin/misc/file_manager/static/js/utility.js', debugger: './pgadmin/tools/debugger/static/js/index.js', 'pgadmin.style': pgadminCssStyles, pgadmin: pgadminScssStyles, @@ -535,7 +534,6 @@ module.exports = [{ imports: [ 'pure|pgadmin.about', 'pure|pgadmin.preferences', - 'pure|pgadmin.file_manager', 'pure|pgadmin.settings', 'pure|pgadmin.tools.backup', 'pure|pgadmin.tools.restore', @@ -546,7 +544,7 @@ module.exports = [{ 'pure|pgadmin.tools.debugger', 'pure|pgadmin.node.pga_job', 'pure|pgadmin.tools.schema_diff', - 'pure|pgadmin.tools.storage_manager', + 'pure|pgadmin.tools.file_manager', 'pure|pgadmin.tools.search_objects', 'pure|pgadmin.tools.erd_module', 'pure|pgadmin.tools.psql_module', diff --git a/web/webpack.shim.js b/web/webpack.shim.js index 4d5d13d9b..14cc6ef91 100644 --- a/web/webpack.shim.js +++ b/web/webpack.shim.js @@ -144,7 +144,6 @@ var webpackShimConfig = { 'snap.svg': path.join(__dirname, './node_modules/snapsvg-cjs/dist/snap.svg-cjs'), 'color-picker': path.join(__dirname, './node_modules/@simonwep/pickr/dist/pickr.es5.min'), 'mousetrap': path.join(__dirname, './node_modules/mousetrap'), - 'tablesorter-metric': path.join(__dirname, './node_modules/tablesorter/dist/js/parsers/parser-metric.min'), 'pathfinding': path.join(__dirname, 'node_modules/pathfinding'), 'dagre': path.join(__dirname, 'node_modules/dagre'), 'graphlib': path.join(__dirname, 'node_modules/graphlib'), @@ -205,8 +204,6 @@ var webpackShimConfig = { 'pgadmin.browser.utils': '/browser/js/utils', 'pgadmin.browser.wizard': path.join(__dirname, './pgadmin/browser/static/js/wizard'), 'pgadmin.dashboard': path.join(__dirname, './pgadmin/dashboard/static/js/Dashboard'), - 'pgadmin.file_manager': path.join(__dirname, './pgadmin/misc/file_manager/static/js/file_manager'), - 'pgadmin.file_utility': path.join(__dirname, './pgadmin/misc/file_manager/static/js/utility'), 'pgadmin.help': path.join(__dirname, './pgadmin/help/static/js/help'), 'pgadmin.misc.explain': path.join(__dirname, './pgadmin/misc/static/explain/js/explain'), 'pgadmin.misc.cloud': path.join(__dirname, './pgadmin/misc/cloud/static/js/cloud'), @@ -278,6 +275,7 @@ var webpackShimConfig = { 'pgadmin.tools.debugger': path.join(__dirname, './pgadmin/tools/debugger/static/js/'), 'pgadmin.tools.debugger.ui': path.join(__dirname, './pgadmin/tools/debugger/static/js/debugger_ui'), 'pgadmin.tools.debugger.utils': path.join(__dirname, './pgadmin/tools/debugger/static/js/debugger_utils'), + 'pgadmin.tools.file_manager': path.join(__dirname, './pgadmin/misc/file_manager/static/js'), 'pgadmin.tools.grant_wizard': path.join(__dirname, './pgadmin/tools/grant_wizard/static/js/grant_wizard'), 'pgadmin.tools.import_export': path.join(__dirname, './pgadmin/tools/import_export/static/js/import_export'), 'pgadmin.tools.import_export_servers': path.join(__dirname, './pgadmin/tools/import_export_servers/static/js/'), @@ -286,7 +284,6 @@ var webpackShimConfig = { 'pgadmin.tools.schema_diff': path.join(__dirname, './pgadmin/tools/schema_diff/static/js/schema_diff'), 'pgadmin.tools.schema_diff_ui': path.join(__dirname, './pgadmin/tools/schema_diff/static/js/schema_diff_ui'), 'pgadmin.tools.search_objects': path.join(__dirname, './pgadmin/tools/search_objects/static/js/search_objects'), - 'pgadmin.tools.storage_manager': path.join(__dirname, './pgadmin/tools/storage_manager/static/js/storage_manager'), 'pgadmin.tools.erd_module': path.join(__dirname, './pgadmin/tools/erd/static/js/erd_module'), 'pgadmin.tools.erd': path.join(__dirname, './pgadmin/tools/erd/static/js'), 'pgadmin.tools.psql_module': path.join(__dirname, './pgadmin/tools/psql/static/js/psql_module'), @@ -315,8 +312,8 @@ var webpackShimConfig = { 'pgadmin.browser.server.variable', 'pgadmin.browser.collection', 'pgadmin.browser.node.ui', 'pgadmin.browser.datamodel', 'pgadmin.browser.menu', 'pgadmin.browser.panel', 'pgadmin', 'pgadmin.browser.frame', 'slick.pgadmin.editors', 'slick.pgadmin.formatters', - 'pgadmin.backform', 'pgadmin.backgrid', 'pgadmin.browser', 'pgadmin.file_manager', - 'pgadmin.file_utility', 'pgadmin.browser.node', + 'pgadmin.backform', 'pgadmin.backgrid', 'pgadmin.browser', + 'pgadmin.browser.node', 'pgadmin.alertifyjs', 'pgadmin.settings', 'pgadmin.preferences', 'pgadmin.sqlfoldcode', ], // Checks whether JS module is npm module or not diff --git a/web/webpack.test.config.js b/web/webpack.test.config.js index 438f6ded4..9a2add644 100644 --- a/web/webpack.test.config.js +++ b/web/webpack.test.config.js @@ -212,6 +212,7 @@ module.exports = { 'pgadmin.tools.erd': path.join(__dirname, './pgadmin/tools/erd/static/js'), 'pgadmin.tools.psql': path.join(__dirname, './pgadmin/tools/psql/static/js'), 'pgadmin.tools.sqleditor': path.join(__dirname, './pgadmin/tools/sqleditor/static/js'), + 'pgadmin.tools.file_manager': path.join(__dirname, './pgadmin/misc/file_manager/static/js'), 'pgadmin.authenticate.kerberos': path.join(__dirname, './pgadmin/authenticate/static/js/kerberos'), 'bundled_codemirror': path.join(__dirname, './pgadmin/static/bundle/codemirror'), 'tools': path.join(__dirname, './pgadmin/tools/'), diff --git a/web/yarn.lock b/web/yarn.lock index 31199445f..d088dc86c 100644 --- a/web/yarn.lock +++ b/web/yarn.lock @@ -3200,6 +3200,11 @@ async@^3.2.0: resolved "https://registry.yarnpkg.com/async/-/async-3.2.2.tgz#2eb7671034bb2194d45d30e31e24ec7e7f9670cd" integrity sha512-H0E+qZaDEfx/FY4t7iLRv1W2fFI6+pyCeTw1uN20AQPiwqwM6ojPxHxdLv4z8hi2DtnW9BOckSspLucW7pIE5g== +attr-accept@^2.2.2: + version "2.2.2" + resolved "https://registry.yarnpkg.com/attr-accept/-/attr-accept-2.2.2.tgz#646613809660110749e92f2c10833b70968d929b" + integrity sha512-7prDjvt9HmqiZ0cl5CRjtS84sEyhsHP2coDkaZKRKVfCDo9s7iw7ChVmar78Gu9pC4SoR/28wFu/G5JJhTnqEg== + autoprefixer@^10.2.4: version "10.4.0" resolved "https://registry.yarnpkg.com/autoprefixer/-/autoprefixer-10.4.0.tgz#c3577eb32a1079a440ec253e404eaf1eb21388c8" @@ -4221,6 +4226,14 @@ convert-source-map@~1.1.0: resolved "https://registry.yarnpkg.com/convert-source-map/-/convert-source-map-1.1.3.tgz#4829c877e9fe49b3161f3bf3673888e204699860" integrity sha1-SCnId+n+SbMWHzvzZziI4gRpmGA= +convert-units@^2.3.4: + version "2.3.4" + resolved "https://registry.yarnpkg.com/convert-units/-/convert-units-2.3.4.tgz#a279f4b3cb9b5d5094beba61abc742dcb46a180d" + integrity sha512-ERHfdA0UhHJp1IpwE6PnFJx8LqG7B1ZjJ20UvVCmopEnVCfER68Tbe3kvN63dLbYXDA2xFWRE6zd4Wsf0w7POg== + dependencies: + lodash.foreach "2.3.x" + lodash.keys "2.3.x" + cookie@~0.4.1: version "0.4.1" resolved "https://registry.yarnpkg.com/cookie/-/cookie-0.4.1.tgz#afd713fe26ebd21ba95ceb61f9a8116e50a537d1" @@ -4787,11 +4800,6 @@ domutils@^2.5.2, domutils@^2.6.0, domutils@^2.7.0: domelementtype "^2.2.0" domhandler "^4.2.0" -dropzone@^5.9.3: - version "5.9.3" - resolved "https://registry.yarnpkg.com/dropzone/-/dropzone-5.9.3.tgz#b3070ae090fa48cbc04c17535635537ca72d70d6" - integrity sha512-Azk8kD/2/nJIuVPK+zQ9sjKMRIpRvNyqn9XwbBHNq+iNuSccbJS6hwm1Woy0pMST0erSo0u4j+KJaodndDk4vA== - duplexer2@^0.1.2, duplexer2@~0.1.0, duplexer2@~0.1.2: version "0.1.4" resolved "https://registry.yarnpkg.com/duplexer2/-/duplexer2-0.1.4.tgz#8b12dab878c0d69e3e7891051662a32fc6bddcc1" @@ -5343,6 +5351,13 @@ file-entry-cache@^6.0.1: dependencies: flat-cache "^3.0.4" +file-selector@^0.6.0: + version "0.6.0" + resolved "https://registry.yarnpkg.com/file-selector/-/file-selector-0.6.0.tgz#fa0a8d9007b829504db4d07dd4de0310b65287dc" + integrity sha512-QlZ5yJC0VxHxQQsQhXvBaC7VRJ2uaxTf+Tfpu4Z/OcVQJVpZO+DGU0rkoVW5ce2SccxugvpBJoMvUs59iILYdw== + dependencies: + tslib "^2.4.0" + file-type@^12.0.0: version "12.4.2" resolved "https://registry.yarnpkg.com/file-type/-/file-type-12.4.2.tgz#a344ea5664a1d01447ee7fb1b635f72feb6169d9" @@ -6493,7 +6508,7 @@ jquery-ui@>=1.8.0, jquery-ui@^1.13.0: dependencies: jquery ">=1.8.0 <4.0.0" -jquery@>=1.2.6, "jquery@>=1.7.1 <4.0.0", jquery@>=1.8.0, "jquery@>=1.8.0 <4.0.0", jquery@^3.3.1, jquery@^3.5.0, jquery@^3.5.1, jquery@^3.6.0: +"jquery@>=1.7.1 <4.0.0", jquery@>=1.8.0, "jquery@>=1.8.0 <4.0.0", jquery@^3.3.1, jquery@^3.5.0, jquery@^3.5.1, jquery@^3.6.0: version "3.6.0" resolved "https://registry.yarnpkg.com/jquery/-/jquery-3.6.0.tgz#c72a09f15c1bdce142f49dbf1170bdf8adac2470" integrity sha512-JVzAR/AjBvVt2BmYhxRCSYysDsPcssdmTFnzyLEts9qNwmjmu4JTAMYubEfwVOSwpQ1I1sKKFcxhZCI2buerfw== @@ -6910,6 +6925,44 @@ locate-path@^6.0.0: dependencies: p-locate "^5.0.0" +lodash._basebind@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._basebind/-/lodash._basebind-2.3.0.tgz#2b5bc452a0e106143b21869f233bdb587417d248" + integrity sha512-SHqM7YCuJ+BeGTs7lqpWnmdHEeF4MWxS3dksJctHFNxR81FXPOzA4bS5Vs5CpcGTkBpM8FCl+YEbQEblRw8ABg== + dependencies: + lodash._basecreate "~2.3.0" + lodash._setbinddata "~2.3.0" + lodash.isobject "~2.3.0" + +lodash._basecreate@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._basecreate/-/lodash._basecreate-2.3.0.tgz#9b88a86a4dcff7b7f3c61d83a2fcfc0671ec9de0" + integrity sha512-vwZaWldZwS2y9b99D8i9+WtgiZXbHKsBsMrpxJEqTsNW20NhJo5W8PBQkeQO9CmxuqEYn8UkMnfEM2MMT4cVrw== + dependencies: + lodash._renative "~2.3.0" + lodash.isobject "~2.3.0" + lodash.noop "~2.3.0" + +lodash._basecreatecallback@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._basecreatecallback/-/lodash._basecreatecallback-2.3.0.tgz#37b2ab17591a339e988db3259fcd46019d7ac362" + integrity sha512-Ev+pDzzfVfgbiucpXijconLGRBar7/+KNCf05kSnk4CmdDVhAy1RdbU9efCJ/o9GXI08JdUGwZ+5QJ3QX3kj0g== + dependencies: + lodash._setbinddata "~2.3.0" + lodash.bind "~2.3.0" + lodash.identity "~2.3.0" + lodash.support "~2.3.0" + +lodash._basecreatewrapper@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._basecreatewrapper/-/lodash._basecreatewrapper-2.3.0.tgz#aa0c61ad96044c3933376131483a9759c3651247" + integrity sha512-YLycQ7k8AB9Wc1EOvLNxuRWcqipDkMXq2GCgnLWQR6qtgTb3gY3LELzEpnFshrEO4LOLs+R2EpcY+uCOZaLQ8Q== + dependencies: + lodash._basecreate "~2.3.0" + lodash._setbinddata "~2.3.0" + lodash._slice "~2.3.0" + lodash.isobject "~2.3.0" + lodash._baseisequal@^3.0.0: version "3.0.7" resolved "https://registry.yarnpkg.com/lodash._baseisequal/-/lodash._baseisequal-3.0.7.tgz#d8025f76339d29342767dcc887ce5cb95a5b51f1" @@ -6924,11 +6977,59 @@ lodash._bindcallback@^3.0.0: resolved "https://registry.yarnpkg.com/lodash._bindcallback/-/lodash._bindcallback-3.0.1.tgz#e531c27644cf8b57a99e17ed95b35c748789392e" integrity sha1-5THCdkTPi1epnhftlbNcdIeJOS4= +lodash._createwrapper@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._createwrapper/-/lodash._createwrapper-2.3.0.tgz#d1aae1102dadf440e8e06fc133a6edd7fe146075" + integrity sha512-XjaI/rzg9W+WO4WJDQ+PRlHD5sAMJ1RhJLuT65cBxLCb1kIYs4U20jqvTDGAWyVT3c34GYiLd9AreHYuB/8yJA== + dependencies: + lodash._basebind "~2.3.0" + lodash._basecreatewrapper "~2.3.0" + lodash.isfunction "~2.3.0" + lodash._getnative@^3.0.0: version "3.9.1" resolved "https://registry.yarnpkg.com/lodash._getnative/-/lodash._getnative-3.9.1.tgz#570bc7dede46d61cdcde687d65d3eecbaa3aaff5" integrity sha1-VwvH3t5G1hzc3mh9ZdPuy6o6r/U= +lodash._objecttypes@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._objecttypes/-/lodash._objecttypes-2.3.0.tgz#6a3ea3987dd6eeb8021b2d5c9c303549cc2bae1e" + integrity sha512-jbA6QyHt9cw3BzvbWzIcnU3Z12jSneT6xBgz3Y782CJsN1tV5aTBKrFo2B4AkeHBNaxSrbPYZZpi1Lwj3xjdtg== + +lodash._renative@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._renative/-/lodash._renative-2.3.0.tgz#77d8edd4ced26dd5971f9e15a5f772e4e317fbd3" + integrity sha512-v44MRirqYqZGK/h5UKoVqXWF2L+LUiLTU+Ogu5rHRVWJUA1uWIlHaMpG8f/OA8j++BzPMQij9+erXHtgFcbuwg== + +lodash._setbinddata@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._setbinddata/-/lodash._setbinddata-2.3.0.tgz#e5610490acd13277d59858d95b5f2727f1508f04" + integrity sha512-xMFfbF7dL+sFtrdE49uHFmfpBAEwlFtfgMp86nQRlAF6aizYL+3MTbnYMKJSkP1W501PhsgiBED5kBbZd8kR2g== + dependencies: + lodash._renative "~2.3.0" + lodash.noop "~2.3.0" + +lodash._shimkeys@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._shimkeys/-/lodash._shimkeys-2.3.0.tgz#611f93149e3e6c721096b48769ef29537ada8ba9" + integrity sha512-9Iuyi7TiWMGa/9+2rqEE+Zwye4b/U2w7Saw6UX1h6Xs88mEER+uz9FZcEBPKMVKsad9Pw5GNAcIBRnW2jNpneQ== + dependencies: + lodash._objecttypes "~2.3.0" + +lodash._slice@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._slice/-/lodash._slice-2.3.0.tgz#147198132859972e4680ca29a5992c855669aa5c" + integrity sha512-7C61GhzRUv36gTafr+RIb+AomCAYsSATEoK4OP0VkNBcwvsM022Z22AVgqjjzikeNO1U29LzsJZDvLbiNPUYvA== + +lodash.bind@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.bind/-/lodash.bind-2.3.0.tgz#c2a8e18b68e5ecc152e2b168266116fea5b016cc" + integrity sha512-goakyOo+FMN8lttMPnZ0UNlr5RlzX4IrUXyTJPT2A0tGCMXySupond9wzvDqTvVmYTcQjIKGrj8naJDS2xWAlQ== + dependencies: + lodash._createwrapper "~2.3.0" + lodash._renative "~2.3.0" + lodash._slice "~2.3.0" + lodash.debounce@^4.0.8: version "4.0.8" resolved "https://registry.yarnpkg.com/lodash.debounce/-/lodash.debounce-4.0.8.tgz#82d79bff30a67c4005ffd5e2515300ad9ca4d7af" @@ -6944,6 +7045,28 @@ lodash.flattendeep@^4.4.0: resolved "https://registry.yarnpkg.com/lodash.flattendeep/-/lodash.flattendeep-4.4.0.tgz#fb030917f86a3134e5bc9bec0d69e0013ddfedb2" integrity sha1-+wMJF/hqMTTlvJvsDWngAT3f7bI= +lodash.foreach@2.3.x: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.foreach/-/lodash.foreach-2.3.0.tgz#083404c91e846ee77245fdf9d76519c68b2af168" + integrity sha512-yLnyptVRJd0//AbGp480grgQG9iaDIV5uOgSbpurRy1dYybPbjNTLQ3FyLEQ84buVLPG7jyaiyvpzgfOutRB3Q== + dependencies: + lodash._basecreatecallback "~2.3.0" + lodash.forown "~2.3.0" + +lodash.forown@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.forown/-/lodash.forown-2.3.0.tgz#24fb4aaf800d45fc2dc60bfec3ce04c836a3ad7f" + integrity sha512-dUnCsuQTtq3Y7bxPNoEEqjJjPL2ftLtcz2PTeRKvhbpdM514AvnqCjewHGsm/W+dwspIwa14KoWEZeizJ7smxA== + dependencies: + lodash._basecreatecallback "~2.3.0" + lodash._objecttypes "~2.3.0" + lodash.keys "~2.3.0" + +lodash.identity@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.identity/-/lodash.identity-2.3.0.tgz#6b01a210c9485355c2a913b48b6711219a173ded" + integrity sha512-NYJ2r2cwy3tkx/saqbIZEX6oQUzjWTnGRu7d/zmBjMCZos3eHBxCpbvWFWSetv8jFVrptsp6EbWjzNgBKhUoOA== + lodash.isarguments@^3.0.0: version "3.1.0" resolved "https://registry.yarnpkg.com/lodash.isarguments/-/lodash.isarguments-3.1.0.tgz#2f573d85c6a24289ff00663b491c1d338ff3458a" @@ -6967,11 +7090,32 @@ lodash.isequal@^4.5.0: resolved "https://registry.yarnpkg.com/lodash.isequal/-/lodash.isequal-4.5.0.tgz#415c4478f2bcc30120c22ce10ed3226f7d3e18e0" integrity sha1-QVxEePK8wwEgwizhDtMib30+GOA= +lodash.isfunction@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.isfunction/-/lodash.isfunction-2.3.0.tgz#6b2973e47a647cf12e70d676aea13643706e5267" + integrity sha512-X5lteBYlCrVO7Qc00fxP8W90fzRp6Ax9XcHANmU3OsZHdSyIVZ9ZlX5QTTpRq8aGY+9I5Rmd0UTzTIIyWPugEQ== + +lodash.isobject@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.isobject/-/lodash.isobject-2.3.0.tgz#2e16d3fc583da9831968953f2d8e6d73434f6799" + integrity sha512-jo1pfV61C4TE8BfEzqaHj6EIKiSkFANJrB6yscwuCJMSRw5tbqjk4Gv7nJzk4Z6nFKobZjGZ8Qd41vmnwgeQqQ== + dependencies: + lodash._objecttypes "~2.3.0" + lodash.istypedarray@^3.0.0: version "3.0.6" resolved "https://registry.yarnpkg.com/lodash.istypedarray/-/lodash.istypedarray-3.0.6.tgz#c9a477498607501d8e8494d283b87c39281cef62" integrity sha1-yaR3SYYHUB2OhJTSg7h8OSgc72I= +lodash.keys@2.3.x, lodash.keys@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.keys/-/lodash.keys-2.3.0.tgz#b350f4f92caa9f45a4a2ecf018454cf2f28ae253" + integrity sha512-c0UW0ffqMxSCtoVbmVt2lERJLkEqgoOn2ejPsWXzr0ZrqRbl3uruGgwHzhtqXxi6K/ei3Ey7zimOqSwXgzazPg== + dependencies: + lodash._renative "~2.3.0" + lodash._shimkeys "~2.3.0" + lodash.isobject "~2.3.0" + lodash.keys@^3.0.0: version "3.1.2" resolved "https://registry.yarnpkg.com/lodash.keys/-/lodash.keys-3.1.2.tgz#4dbc0472b156be50a0b286855d1bd0b0c656098a" @@ -6996,6 +7140,18 @@ lodash.merge@^4.6.2: resolved "https://registry.yarnpkg.com/lodash.merge/-/lodash.merge-4.6.2.tgz#558aa53b43b661e1925a0afdfa36a9a1085fe57a" integrity sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ== +lodash.noop@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.noop/-/lodash.noop-2.3.0.tgz#3059d628d51bbf937cd2a0b6fc3a7f212a669c2c" + integrity sha512-NpSm8HRm1WkBBWHUveDukLF4Kfb5P5E3fjHc9Qre9A11nNubozLWD2wH3UBTZbu+KSuX8aSUvy9b+PUyEceJ8g== + +lodash.support@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.support/-/lodash.support-2.3.0.tgz#7eaf038af4f0d6aab776b44aa6dcfc80334c9bfd" + integrity sha512-etc7VWbB0U3Iya8ixj2xy4sDBN3jvPX7ODi8iXtn4KkkjNpdngrdc7Vlt5jub/Vgqx6/dWtp7Ml9awhCQPYKGQ== + dependencies: + lodash._renative "~2.3.0" + lodash.truncate@^4.4.2: version "4.4.2" resolved "https://registry.yarnpkg.com/lodash.truncate/-/lodash.truncate-4.4.2.tgz#5a350da0b1113b837ecfffd5812cbe58d6eae193" @@ -7376,7 +7532,7 @@ moment-timezone@^0.5.34: dependencies: moment ">= 2.9.0" -moment@^2.29.4: +"moment@>= 2.9.0", moment@^2.29.0, moment@^2.29.4, moment@~2.29.2: version "2.29.4" resolved "https://registry.yarnpkg.com/moment/-/moment-2.29.4.tgz#3dbe052889fe7c1b2ed966fcb3a77328964ef108" integrity sha512-5LC9SOxjSc2HF6vO2CyuTDNivEdoz2IvyJJGj6X8DJ0eFyfszE0QiEd+iXmBvUP3WHxSjFH/vIsA0EN00cgr8w== @@ -8245,6 +8401,15 @@ prop-types@^15.5.8, prop-types@^15.6.0, prop-types@^15.6.2, prop-types@^15.7.2: object-assign "^4.1.1" react-is "^16.8.1" +prop-types@^15.8.1: + version "15.8.1" + resolved "https://registry.yarnpkg.com/prop-types/-/prop-types-15.8.1.tgz#67d87bf1a694f48435cf332c24af10214a3140b5" + integrity sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg== + dependencies: + loose-envify "^1.4.0" + object-assign "^4.1.1" + react-is "^16.13.1" + public-encrypt@^4.0.0: version "4.0.3" resolved "https://registry.yarnpkg.com/public-encrypt/-/public-encrypt-4.0.3.tgz#4fcc9d77a07e48ba7527e7cbe0de33d0701331e0" @@ -8554,6 +8719,15 @@ react-draggable@^4.4.4: clsx "^1.1.1" prop-types "^15.6.0" +react-dropzone@^14.2.1: + version "14.2.1" + resolved "https://registry.yarnpkg.com/react-dropzone/-/react-dropzone-14.2.1.tgz#aad17e06290723358398a7be76fb38ecf6d77c1a" + integrity sha512-jzX6wDtAjlfwZ+Fbg+G17EszWUkQVxhMTWMfAC9qSUq7II2pKglHA8aarbFKl0mLpRPDaNUcy+HD/Sf4gkf76Q== + dependencies: + attr-accept "^2.2.2" + file-selector "^0.6.0" + prop-types "^15.8.1" + react-input-autosize@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/react-input-autosize/-/react-input-autosize-3.0.0.tgz#6b5898c790d4478d69420b55441fcc31d5c50a85" @@ -9775,13 +9949,6 @@ table@^6.0.9: string-width "^4.2.3" strip-ansi "^6.0.1" -tablesorter@^2.31.2: - version "2.31.3" - resolved "https://registry.yarnpkg.com/tablesorter/-/tablesorter-2.31.3.tgz#94c33234ba0e5d9efc5ba4e48651010a396c8b64" - integrity sha512-ueEzeKiMajDcCWnUoT1dOeNEaS1OmPh9+8J0O2Sjp3TTijMygH74EA9QNJiNkLJqULyNU0RhbKY26UMUq9iurA== - dependencies: - jquery ">=1.2.6" - tapable@^2.1.1, tapable@^2.2.0: version "2.2.1" resolved "https://registry.yarnpkg.com/tapable/-/tapable-2.2.1.tgz#1967a73ef4060a82f12ab96af86d52fdb76eeca0" @@ -9948,6 +10115,11 @@ tslib@^2.2.0: resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.3.1.tgz#e8a335add5ceae51aa261d32a490158ef042ef01" integrity sha512-77EbyPPpMz+FRFRuAFlWMtmgUWGe9UOG2Z25NqCwiIjRhOf5iKGuzSe5P2w1laq+FkRy4p+PCuVkJSGkzTEKVw== +tslib@^2.4.0: + version "2.4.0" + resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.4.0.tgz#7cecaa7f073ce680a05847aa77be941098f36dc3" + integrity sha512-d6xOpEDfsi2CZVlPQzGeux8XMwLT9hssAsaPYExaQMuYskwb+x1x7J371tWlbBdWHroy99KnVB6qIkUbs5X3UQ== + ttf2eot@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/ttf2eot/-/ttf2eot-2.0.0.tgz#8e6337a585abd1608a0c84958ab483ce69f6654b"