From f706caf131f9c5e872ede18fb7957f02251c9220 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Sun, 6 Mar 2022 17:41:52 +0100 Subject: [PATCH 01/34] Assets: added favicon --- www/favicon.ico | Bin 0 -> 111830 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 www/favicon.ico diff --git a/www/favicon.ico b/www/favicon.ico new file mode 100644 index 0000000000000000000000000000000000000000..0f09ae9138ec9eddfc2dabdb138d6ee1760d1e13 GIT binary patch literal 111830 zcmeDk2RxR~|9Nd?lZ=d1D3R=xkx@xWMJmbOk}^`rD>5RbB_ykmz0)!aWs^-r$*7P$ z-~T=S^pl_QTBTpz$9dj+o_p@T>+ZSx-uJ!-K?n#3f&&6#gmkt*kQVrjME*a`iid#m zz&%mXv9uTj_3$GgPR{?QgEv4B{RQwQ<5-#mf--y%5DB=BmWKsFhEWK}Nmgbz;R>1+ zplCv=JralDr*OoBt3Giy7}U9CiFd2u_boOtO5IpL`R|b3+Cs#h3>u@>!KkX1&mowG zoYg93Hd%Q&n^HEpVQ}h86r}241r(_s)*p%23F8nn+c>0w5f%K|;{L-P-ew|sg=&aQ zvBcrE*zB{U_H|+O6+v=91~@0~rv_uGZb80K8M)SpIoFPfnA!pPqKFP zMv(t*K^^t!O=ez^>oDC(3w5A$ghtxkAWKdYNS;7=ukQh>AyRI$^R(URRj3^Y$*pQ1 zl-|To!LqL&p`nnM`o=HU-NRqn_(bTKg5M+ET59Ab!6dCdXbonRcv<{#ye4kXGofu3 zt9U#1G`kvVvLtl5MG`WzkRwI0I~7RJ-|k_g!7X5iRzL!hnXA@sxtqYPPEDFj=t~f0 z&d)*1Cdkpuq=7-Q-a3_rwx1KnrIsxCS(CZggG)BO(1@4PL6ISo!tx7+2q}~lGm?{5 zSYOE{qTO7pTH0=e1a*>uhz4m(utQAn#gj7?iJktKH$1bjNN{RaB;jgjAiK)VY9euT zgc0X;XuPiRndS^(lfHQAlAlL6Q1(8?s?FySM-BVn3M@B#M!RpHBGwk&Hes^jYpujO zWbi^|_?+cBPUKmoPI~57BN%v*tJyd1U=s}1Sx+vCXR_uDZIOk`Rn@v(7($ML^j7C1 zx8xD~Qq{3Q&oLzrJRI(B4(&Bf-h;U@pIm1xk|66%?HX)RBGH>vi7vbx z@zEoiC69#s8?LPQ=AavO>6m^bBlb0n#5LbW5+paIBx{MVb6hy{{PSjlt^Jt1qDS6U z<;C6CBi?N=EP+7@?XiFU7>K59j!PzOOH0DNs=-~luS-{*jaS3VV$i)laKKXV6}5Z6 zqGbG4rpvL6ZI9e&?)FP_CfA3CUQ}ykf^c(yi=^Qs? zySxh%scjNiOSy$kk;6J6!|hxQA&1u!R};x(7pFTIO&bL7v!<#TsMDRR6qWR0XJFaA zg2302C`E6DR)kA2#RxuToA{9tBPNowe(esPX(C(hKF(Vw=(~r}0io#E)>r#*yZYfa zL?I^QS!Y)k8d5h*J2qea;jVO0?P5ksvjQk1%0Cld zGJ4i@^Z~M~{m~m^@lRpRY=R_gZjsPxnyna^Ma(8=EzUMxGFpukC|oOrP=|0+hF0nY z4`fCwwcYlqP7pKM7syPW^7upk#ax*O`|JYQ*O!zMp1t)lgy!yfZcGuDwB##yDBjSy zY}v_-jQmhL5@KuM`UL9&#kWTcq*Ru>RIPC2K5eI^yh=&uy79Fz@^nG?+qV@gY}R&+ zvNSgb)|;S=3Zw7dHb6jBg8I35tX)i=3GeSP5jGGYeFkpFtcFSAfS7|fx)iP z*VTs##k5O_`8HkcwJ=C9ZS}eNiEfuBLy8;L25AJlyj&*x_1hwztP*<FynS=;w$vqa|HDAET;7gt8$Lfc2p%vYOtut zq(WQo0-OnKmIlP_F7Q6zJ?Kd4-CGimf6r zuhiu2sgpZ)ne4E?5-bcU>EByaz$^1xW70V7(ikAR3?fZlfU4 zMlMn#Ooa7o@1C=`h0###ctPR+_xhLTyCUNMx>)8O%p{X>P}1FTv$B$aw#hve< zl0L<)ZHn4)7=qhGQlW3o8oe#nIUY?uQg|PKKJ>=t`K=pAA!v2{cy8QD3F+OnH@GGt*aB z8DVL+gJ}moU}5WCgetYJWsPIiNuH1CrMJA1*s%(|j0O6P6`$QV=VSZRT3sEk4~|;geub@eg6{##v-eKt(sWP1d6whyhGxr~e189!r=%y7 zH!3>aK$z^WIHGW$Q>*uBsH?N<$Etm|A^W`JU)p(}YE{*|+pSu7)1v5RP19X^hlpcN zdpZ-Z-zT%ZC9(Ph(W?6bxN0?K7M~q}UqHZed;(+PR-wSjQ8~s3OPo1IzFcrVEsI=7k+`_BDZw zY`l~K_L>bX&o^rXy%IZkDLMXWUb)o+jMLU;1Pq3ocA9!0Fgf^8WvdyN`3|?UIt@3@ z_y^c*>k(E?B&n35-{&iWQ5rI27(^JmyEpAFn;?^LM)^bhD`HKx8>p=WH>heDGM_y9 z7_t3{*J(EQlM?M?O(}Sye+b%)qm$Tl6yqU@s!A`# z4zo|PU9C6P+<8OH6OV^ua!QZ%v(Ry;H#8OeD)JI zN$<7pYp+Dh`n%>bX^+p>ueobxMZB5yv$L6$q1~ge*0zq=mrl_+tZGdP{-t@iA| zA#$arl0sX5A(r*MtRk1JIfC%=so~_HV&m{vwJZICI89N zgChRKb(DeJ<>0>biHjmnVV@s*V#(>YU57G zWZyM%x;NHT)$3OAD_5-wL8QCh;M^$DSJfdAZ=9Gc@HyF2HMT6#q@YvcE|K%|Ud)tp zD`U=}x=tjnX|$*;U%`1 zgp*yL;)rYtp*<+yDybR2Ix|~O_V6d$1I4LAQ>a|!2D4o34BFG?fyX^fQU0ySWh!l60(1T}^NH1t; zVeK!A7b#O%)Biq#S0scWbG1D?LZjx}O2s=Cb*H5ce#QUPi<515xILxogbR(RUmp zqYOJc*E$MvrqbUmJtf}nXMH(LW$k`QTs!9?^qucdMknA%^IR8&nRnb05Non%r(uB^Ye; zSfS8m;;Uo`B`$JV0e|BMxei8~u6!YqOx<7cgx}%AO0k~So_MZG_#+jP$~q0daH?V#MV4Kll)+%l8m zcyM7euTIBRRjaDYpDSx($j=O374oyQpff>IFu4rMXuHsOlJ`8UT+3G!k+GSYtCLXN z`qtV#H+PUd*k_B+M~iP?rAz+qNy!nb?GA?T#7^eRt@jLTwqEPCm&#aj_u=jXRH7UF zTjgJg@LJ~yrXTY1!&hm)S0aOCxGZTgoXlRTX`8N~6CPlB?$ z20_bxCP9LLM~oL7?-I5)^K1sAD5cPHKT8JRRJE^Hqj#JkO7t$>2hHb3S4HVe?v=9fewi$m* zQ!$YeS9q+haipu$o&$VsEAsf(Sze<+WtI0>*(Tjudz)9g{iO-h1sWvpkzA}4di(y* zeqs_?oaW6jVs@<#nu>aAa-NxVMWm!QH+=PpwTP(by0*&{Sm)-X9v1b*hptjsDY$5S z#DaMCyYU`6dx_keoo|cSLDmn(Om?^T$M^1U;fd2OD8ui;z%u7aK5b80#&r|V>kv&G z_

kwrrO&uTN-{HH2=YQjvd_ymT7zLFQ{n{G-JQ&$T+il zJATc}d+{U}n*a<`2|Q(?G~!DyT&eqc^;w{R$2rd`nVvBzv2IAcEO+2RIANbXMqQ6f zwNu%NGlN(7lzsPqYfM61KZ`3`I;0tw5{bVp_!Xyt5l&Q#k!N~D%BezXZ^V^@a;7%< zjXH<5cYBc|-;5YQHznMK<-+bkR4yUM8}bNUjH}q6g=K$~B@~ITurpNIg-WoD+K;c2 z6=u3Zl-r3_t?J0rywaL8cWkccH6-93=u8Ydj(Traxi8r)72?CtBJ_xlD0vZgYA>|u zj3DB$YQ-n9?2uMVovszz<9JyK>h@heqo^J)ZKl|>C47@cg``rr7}cw!7LM@YqoL#} zQQMUjb|#XGZYk6xdU&N}*IRyj6YTHb~pAM`s? zOWmXU1>r)jR4E(UtJgjdUO`+}%p>lw^>zKq)-RNvNo!onZ`r4=qrCVwBtLE-kEirb zFI2GGL{&VzFf{d3Y$IDro_NOBo2S3D5Q`sR;o?n0W*lA>etf84fD-wYw%|_wvHgk$S-j z66D^SUqW+Xf2dEoZr43La%qgF0bwf)2Jh4I7+E>q1#Zaq{?gP$1a;-Q>THJuz|e19 z$MfgD62)PL7|a_^2=mtMU#oZwkop_h`wJkaoIg&0Apb#%+>u^B(_mt483-!%YF!qDUX^Tmy6o~J;uP=v4+YBgNn~0 z+yQT$q&vqwF#b7exVPO^{9^&ZNUDMye_C2M!_!xaoZ*=Y*aNsL1rVI?S3rJMM(^zM z;clzzpGGHf~}iS_1i#k=}?UnCha{g}^g3Hri^Wbex#(R|*a zarH>b`y$WlO3yy*^KPn-cTz5XAK&DX$JnjD%Q@6kaUXQvSb?mWhv~XCtrN|2nvoX` zx0)3ZCw*MK9o~qW4WGizzrvyB)i?CibhRnA4fP9Fq(ToRTYO09R$0y!cYH`H`2@M& z4Ruiwt%;F0fz%eyoB*jx|9V4BnS_XL8SHgI%lfdMenzKfs*!_ z*hqu~8@}w+@4aiLXJqP4Y<&@>vd727K{~Xsj#sF+thX)myxTdM5FcW;`Q@hx?4zbtS z9U>-IBH?ZyFx?S*VRfDy&Gu}LqnR=a>Lt4!#D(9Q2Kpmbeae;Z5d{cp_L|~Rl4=fG z_GoE;<@18ReR@tRE<51F;dpG#rft`{6%Sk?YM?DK72XklR^h1N6EHwyw=6xMH~4Yd@5f(P98?^Osg-22|)Mh{-L#AX*)DH-cN3l_Pb#55r3R z{2}|ApfmoPO^gY}{9>MNt)#@XQX~^_#HtGy@^WIO8_~~u^i6O_oB_9)mG0+KMVkwQ zo$BU>xrXNH)f>-6gcP2|_x%voeZ+(&3t0qBB)%R9md^|wNZZqa+9-Rs}>0^?oEiSh}>VVTUo!PWH5Tr$XpR|^<;7Z z{d4G@d@Zf+i7y*`tn$?ipAn1<%E1UTrRwVusq}c=G*qhxQsiPpTuJ7IVs>K z^U@>uBDO4kwdHQq!;#D^k5CGT3lUeB^~f{$_$jl95JYzEyVHGv>-^d)@`?piQ@M6uF8acMJ?5TON*J-lU`lYjKcPGZwOP1Yj!Do(>$dz`^$Nv7_QwG?Q+amL zk|T*g{wqyncfFO1{hABA*LC)r?ub^yeX}X&iQ=LD{#`=`2cvZxR<08fJtYlcxndUt za%TqY?c#+X9=dzqyhKjD+GfkoNLbplCGY)xZQ;y_ExC^k#gS(@J*{x{m=P&Bj4NE_ z30-RFh93?jIOGTkn7e^v6aJ@QvqZ%HFB}Zs8j;Wm~e`V`!k1&jomz{MsU_~H|)_Ryoh>ZW*}tF;i)~Wgw?k3xM0#L zcF52Z!K#hmv&GA5^QPRdoj<%9r@c9^7@k_F`rP}_*?Kf~1g~-Ut8)2sR9M*1Y84f2 zY5Be)eB^svlK4D{q$!aP`hj6g;p6ur1|sG}45#qh zvP6$b3XSx&xayqzQns0?va%>ySId*p0&xSs4nv8nVXMB$7J{}a`mGU^{7Ss{vQ@?3 zJIeIs`4Vil)@Kl|wk)DpC0a}kCQPZ-Z@E_BGF|e&zM*lw9fJ>cz^nLH_aSWZ0zAec z^1S`_cze1N3nPumR$K`3^F6R#@8*MY2yIsQ!0r_(mFiS z_7|vT`-%XI^gz$#n_EgX)2pLjxYckFN!M1FncP>tyVWyrg|p#Wse;sjJ6E$a9`_lV zyiV|J4A5f~Bo`HPq3f;Q0mbg>jgk0>@~qNLw{!FED8gLlR<#cM3bGKNH2c;=ls~th zz;$c$*H}hLIfwJvbC|A3co#Kvyd<_)Pjk$R3N5vCKjrf|qoLD5t#QB5do%mT0Yx9L zAKv}4A%I5rq0LaX^hg?UlF*HvtmI0!jHG0Y)G`Q#+B2Uy_?`Zw!Ft8?{?KZ2hK7`` zR*Sl?Qo}&ALOz6zSr-?&M_R9gXVbZ!|x1t)%d8bKxE zAKSz!7I@&(`W;CstOF)8D=OZ~xQo9cOgB!eJR4I*p%G{wWU9Vao*+&D(WIXn*!saG z^~Jq2y8KQY2U%;jB@t^?7m&N+F+6iMt=h`PPp*7Rjyg$dS7w*_(AgvOD+c0-tJX96 z>V9a*cu!X##6k+bv765u+PtTFcB7?RWKHE0E??_+1{hgu1ccMS?oE_5@eo_PwbW)~ znMvvw{vH=kCpHd;D?=xB1x_44wTDdBu^`Bpj6RWlHRjWYcJbe=a}5s{Y~V($!_{V5 zTk87e_?8x$IGq|iJCEj92TpPfu@(^XctL^$$u&D4R1?Hm<|W>alRn!pqWgrZ*IOp) zSX@wYI8cXmeYt0+9;7Er_VVKSj;&_ZTa)-3U7D{FeQCHXH*(szQogIr(}na2b)u!H zprxm4@yBk}T0x~K?y%x52Mn!v>m;djnUVLND^l6DA~c*hJlvR-Yp^e`+pd@d$|qB& zYbt(i%RZPNe<6*8^tuO)txtYdda&O%N8_r?3L_}zt0WC^epWHG>u@xE70sBEShsD_ zICP8A!nd7aZ$cQJ`I$YPpD z`GAAF`q5gmz(;+n#U&EMtSyEv7z*QMbBDl z_?&GEHKy13qJ4Z#TyCD%2}~7c(K|^NK=+p<;T+8QD(jvD;igP%%EWJ9YbB-OB?(AM34G#Atp@hDiN(%P`SAAF%emU~qWVhwibK*GVTP;I-k?Yj;HQ)3fQn|D11@5wD-_A}c z;wcCLov9Pi!;-rPQ&Y&nx=DgAW-Ss`MC-mU7_%=Q+FWQVsHeks;anG9#j4#g_alzs z_q`6sWbdsMw~GgBH&xFWEJ6gU^q{Q1f&Wb%pVckpoM?`8Mx zBpA`>T&*K7WvV1XltEee(D3!D;i>>_+-pso>sQiLbFVt*(yH#XJ|)L%SU5A;_Q|f$ zy-#%ev3dqAeNtcI)@LLdz@3{WOW2U0Uicd)j<; z%Fe=v$+zCo31zio87uyJI`ly!B9wK?*#kD_f=Em9RnT$|>#K=HX1+7c!yxZ?v;Bo5R|faAcg5@K^7Z zGVx1(O_X~pj4e`olVHNN)pQxJ-rC;MK45U3w<&geRadZ_$6mxm1as?3pjC8^I2Jf$ zD@FNMcq7iu$YwA&az2l{kM?S!tQT3zC+QWuOwUttc1zYeotExQ^fz;7cx^6`V%lHP zRQ5`a+-?(e(O;+esJNNgsm|B`T}aXc^Jc7ctp=Ri zP^k$2F(A!CNRgm&B9#1?|C?W3t5m(8-*rK)~bnr#sUHUan z`ehr8sS4P!H#%{+tqnW8Cgi>JH(MDf$-eW`p7>-u@--Xolhifdx$*Y+Mkkpwq1YbT z$2vLQwST_r>oCkgVS>S0@%+-UUJlH5EG*)cZzz!zn^utSBFv_Y;ichDKB<(DEU^9~ zS3T3K?9<QiGVbmpLeINLxRYZK>tOrmM`nJg856^HOGSQn&MUgV)+eBX@Pw_7q!3csP?6_}{BFy5`8{MQui4ow zuk2mv5xs5A<-SVSEpIv+gTjT^NZ!DpY+Z2*L#0va;)|A>Mz>isjA=c(4l`C``*NMQ z+@ULY@?tM!Mz2@Wp>u;Gili6u7Bc_*Hla5U+v*{7+2Dxy>&DwzYdA;NQ&fsSAi%A| z-)*BuJ5(Mu$P=P(Rp8-9(Z)0Q&hW-%IXV9N@Pat5{7c;oEhpPrhTDYJB=nX?<=mqd z)c&FaWh3lNZ}K`Q?Y!8=Q!Vg(UD4rcqe}U5IgHCe<@F@jDcVFWUGCAGinH3ywzZ** zf!3-52ibNhVsmYx!HJ{9?+MRe!+`(|PxIcA6UI+V$5Rb$5CfCl1Ly8#1Z|hG#e)kw zwO8&lHD`l8{oMpbAyoTP@h&48!MQg``HkChRI zZ*4kOC{DmmFg-9BD&ExMz5R64^LxgEo#L;gSF%aoW--9`)yUp!AK9_0X}}UEO<0Px za*e>r%NeY?U+jt>8QTjb>v?nswZ4&l#o@d1ll!U{JK_;n23R0tl8pDMIwp1Is}kt( zs&o#?so=QYqT#BN!)?&Ld^^)D@|f(Fn0=}Y3{{C5YgV&Uqd2(f?JVi=9+fayJ3Ylo zuRRt}`pDR{+)AKN$jGB3NjY;J?VYQulP>Hphn{TD?p$NbU@PfL``EwUN;`UZWyK24 zOMzSOBt0R{%)VrZ_>9$;kei+9RsWu4GXjY9Caq-aZFkQ(CE>fhiEK9SP8Saj>9|7l zs>noZ^9A)SBT3B?*A?mm1Y3=r?@-<+RSJxBs@bJ*Fhu>P;Mao&d9I8mlvdnKh0Wgt z4JxcDgWk0IH4``}*%U`y!aM7lBFTyQG_PG(5D0Z9t|Uu)(RSSSJnhW)WtGAqX*rsn zkr#J{d5xTpGr!%Wb}^kI83|T|;AQTDmq!%Gx=Q zTd#GPRY<`BXk*IH#gVPbFyIP^ju1K+WBM^4jGzcw1WpHd1jc;KKj{@t@(zPj)@1Vy z4b}_`&%DP5$4}~b9*#@W@&ra`*s*1%YwK@A-y|}bq;{!foW$7$Y+96=1@Aa-l^={$ zzuhYxH6jiLHm`Skz<3KIQ3=~C<{PH}cEpw_?fgw9O%@FsmCoE>E2a$96KmXjkWdjA zi~3q0M%Q{^$5v&N&F&f@3dl$$K4UuF6~u`5ybv8&P?ri%3oh_rrr1K;>((TDTn)}* zm0-E1>PwFrlP6x?1F&TMh?i%7|A!ByGPIJJqtmD&|93wID*;44h%Ig-b)|SeQWsi(4KhjGZ_!*;w8H4lFs+Lh$#;5NNGYZNF9j@Uo=8`qoPi z2Oy3>^X5e375a}co|7T3zbJXwe|0yeN@a?Y z=%XeiyRO`2?tC2{IlzVEx;>axPXx)u^vK|b5#dwiVcI>(kvbJG9V<0?{Wm#fBoy_z zB%NmSJxjuYOHvej?_sbkQKNvYYpqtfh_Gu0RNQCRLG~zN8?aY$4QaR)5V7(3nb(OI0OK&#@|zb8I2+R-TnqU9SRZAMH#g zkUSr!(~Px^t&5E`o~8hgB_XW9J-j464UnO z@*RN~wi6mFeW`7OUXq||gSEV!DL5J+3fuXbWoeTfxklb^) zZr=nT_a^fPDO>ww)jz(Ls#37B4sAM`vzPCbVpRXbt-^c@`A`z;)Sx-m!KCs#x+sf@89r0qHos*FsF5l++B;DdxxxlO~ zoJZ%)O5Hp=vzyS4zLLg(8&aI@P7(dqmU>nCRWb(03Rwl|*{c{Zsyjxpf(+|F)Kx3Ps_u(cR z-Ye%!pGX1E4rE~QN~lFLll<}o|>sF=Pt~aZ%c4#AGG#5e?tjRNu#-^BeNJYBA|)D0MUAGr{uvxfBcwwT2W>s z3AM1Xw~|8NE)se~fr7~nN(CVGTicIz6m^{CNVd_y!1J>?_k6Ema&Z88BPl1bC`;ki zW3u?I0}OiE$(Dw_m4hG3lTtx8+viVCvxY=`jLBQ+^mgZiChF^vIJq6o4}2I2eYkFA zdXxxx-MLmMfxF5HWDfY8n*Zv7Nn2&bDrJ7Ex_(9)h;f(631;I<9@a|gk;B^Zgv)oEtkdq zD`I!|?t5&@iC5^3_ncseu7Ke%@&Ny4w-_KD2_79Qm5SJGSymc<7pPBVkQhF+pOefLN3m`l2$NTy_lF zPAyk0d%phgZi6>>Zf-xhW!n=;zFx`b0pd;dgg(7by?9SSn2(W77ocXSUd20^4l@|) zWX7RaPp~@j++d$=lkWrOBmJaODj)LCuOlk>=F~yQM1!ru>3L+WXGdGGO$WBEvSyl> zuvdb5Rp-qQyEZYaXE3-@An&DG-0Hz3?qTt|7>+@J$%!S3>)0l-1E&rX=^mXef1)dg z@a)jLm%u(dF$ZNuRKeRU6GbMyf*7k$kdqM0kIj?p()O2Y?_mO)*{fKVFZVse8|YWB zx-+5^TcazBoFFvEq(GAnzNGQ*;UGLq1YsVLhxU!wpDsk(?a6AQ9 zH58ig*?lXq7WC{X>Fm7~p$wxcfGXOiR+hq1`81q`cTVC`jqpj~_p} z&RV8)9ZKz>!$D5%s}8;YHpNw5xlX`>9+Hxjk%$mexx@;7BjFpsydJi{|9^mO?f-_q6!=SlzZCdO zfxi^^b0`q0#g7rD!AIe8a5HCwCcjjqCch?#ZXkMt=mVlVh)y6HMr!gM^;hB&yCKKH z8m7)mg!*&H^q;~sR+*as@Dk>=3y66jc7lkSV{8KXBSF*zazp%|BG7*jnFtL562PmI zAcle14&q$-JyZTJP+o9^2A^n*Ixoh5kbJ)#NRpIJ<=OWd3lL3EP7MbT$ z$-@AsqcB8`*ELj~chzr4wEqaefCtnd!r$$0AWp@npK-4hd>1T2)p-AY8-9XZ#b|LO z!c}>8M5*(60-m@1LcULyt->%39{oslUV@)MhCi|jxSt37hTD7ZGUEGWIVcWS=LOy{ z{)WY(fQt?-c7!IM1mO9nWz6@9a?k-}RVV1gR@l$U->?7*M5}VM0p4c-z7PE-ydRf? z5g-Gv!ZrBTf^XIWDDY>#8m++xfpL{M;CcOT#`kglk6&8>{8E1=7w3mH(Alg2?Zz3< zt^YUY{kROYg{kwMjnoprnIA>|oVOx0cm56HB_CC1@Ju-#Nj`U|6}-;f^n{JxX!jeP7FXF zxE0XgXROuytL-f_S?dIAS6qLJ0NCx@hym!o8$@_reYx}IXTet$p~=g9glElvS`0v6 z2Z4DoJg*=8%lm)H{#Vc^?*6X|K*UKg2=M&$U*7+V?-To&_kcdM|1}v1ROKNAc-;i? zchlid6@;>chA z&sF~Uo&%dAn%`9hz*q(!=ye|d<@;Ru{zLw-newRX` zGjfbN zT(p?WRR$u|`Dg&&pa13k;`4rtrh{NSb;R0w`AGnfO}xLnUoyUb?*jmh`y(~@mX$3T z*l&dc;0hU&(TT7w>)%h#A4I*ps*lQWJF^U;5h~R|1C?OB7af{?2K$a+_YS{2038Kx zxCVdB@5K9@d)BD7_vNUefqvAo3L_(^fu1hZr=nLVST<*(DHsoCglq5;{b~UKFq(t- z+vs-U&+J0=efzqs*gh37?e8m4G5W$Y$^f8yP^237FBuO8Df3}~v4}c=;kR1HD-OLe z6}gw?y;KMF+4w&K=Gw^HhuD7lK4f6GBM*50+u7`VDokINyq*fEH=dTW@gIH;_963u zlbC;A0CmFpopKP-f$xVrQCizjX;-vS1rM*F;I{ZS?B-96U9BIdBK5Mom+x=?1MOy@ zcLUfb^HX%hVD3Q-;K-Z-mT6&5ch(&pca01WElYYYH=uIv+e}N#Dd?XMY{ zY^)cn69`n{ISlGuklkK3n9KYP=u_Zba@f3hKPDdoKqtE>8%jd-L=d1%u=YInx!%Ng zGTe;NNB(b4RH~EaLii8An;xdkzu-Oq^d+*OtOe`%lI>LfaurPqG{4P40Y3o?<^KrK z31}_EZ)v#J=$dZD#CAO2-w9{;pay%p(WJnin{61ZNhMuUS}53RxHD*Tz*x<5Cf z9-Ho46uwVrf3M7U8mS+It`jcBa*&4(B8*o}X# zeE@jJesOvKe>sA6T0;YUvryyLJRTkz{3R8`^mu*e+FE&8*;z8+N8?YZgs=g}_vz_%Q2ogmQl?wm&* z=*lAMx%Dwre`njG({kPg0$nStpN4TxFqT5KR^*~aMuz8I9J(*|d}%_Z*sGyUw}tQo zv}pr$zX6~guZ7fw&b!IBCzs89ur@UU6{REioe$AE+flH-a76 z_II^|{@!fL`lfrGRQK$wIftY4dfpd_a{%x-Z52ZbtYg@Ub8G%jcM_5AZm#dE10{&@FpG z`AVZbfC&6t8ECD@L&XD|6m)Qn(HB9ze-$?^Z)bWiJUDrj( zCbRJ$*b*L?clq<}Gk~tU;<5ivnHR!x2JHm0E{%i2TXQKTQc+*{UQSg{}sRFE9FAQ{kJztln<0FCTX% z836e#eJXfD*{)q2J$UR!8PFMp`L0iayH1(dxca#Ej}Fp-RC|6VBnNB0WPW6VDjfDNyoEQW2@Lg?HF#sJgq z69PJ-y~~aNU#bgdBI&fx^8C==KQ|>ktDZibw(R*nfcuifb23xb_mk)j`wv+?UHkXg zzlrN7!GRVH(wwwW@EB@7p)Nfd%=PC#_inGRm`}B{zLV~(gBI>f#D^}h7ECc6{~s#z zP=k7x#o3y$ZeTESftXrNB9iN!XqUJN-pB|Qfo@C#Ls7!2|F0$)DoAp9*uVfhcM*_G-gA+sqqh=L~y(fa5<5TjXDF!*9(Qo<-zGCGgjT zJze{U?}PCHe6I4Zgb`I1?YU@F?`(Pxe5r`c37?vz&_%0%azPc3{pJMABJ&~{?CF__ z{SdJKf%km;G8ms)9A0$WkhfuTYjg10@KS}^)W}~(Tfo;FGcq4MjMU(T_xk=68-S_g ztSt84qLcn}Rl%HS4(n`|DtyR!F(+82qR|5GDbL1#_&F&5=>qDQH-2zG-Ms`pT3|gq zy7pEvdcsR;|JRtGGH?1UkSD{y28anw{=>e#emb1bEaaBV9_Wq71+?&ieeW%$O%m*b z>Q~Sf)LD-1en8+~5I%!ACA4VJ3gMO7vSphfp2n-c(rrL#wB0{$I;5&y5E z)Ar#!3R`L6vl-KWHk^5WmzRwHEv2u~qI=S%CFVa^2l&}^1@(b_KzwsLQwaEzg3oFD zsj!yEc`q6N`#amw!ez<%Uz~v!9E(i*vIuQ~Y1jRx>K8!$tRQwTG8{AF{tnpUFI9l| zbilSHv*GjnqQa7X{~PmDXN6%l80Y+4mDg)39?x_yN}UIu2L#Nyt_AcNAM=uziv6QJ zh4s3#;RCPHE~P#4`;7QmVVDiZIX)i&Yd$mDeN86^U>wK?>YA6&w>iQ%N|UAa&pLvF z$9CwzHQzNSbcDAe;iv2Wo`L<`^YR6AjGG$P2R=ZDW{Z)hsW=lI63#OZ;6E7Kp#x`g z$?JL6G5c$IzIJHAfDW8!W|JNZj>RA+=;JMM#1@!q3>*$v%!0Vbn zi=LpKP;_`aQ=TvlK6p>yf_;FYgEKrfTCxE4e!%)Abl@1(LoC6bB>2pUM6>;9!GI2& zv*Z~JQsr5c^Q6Jtkpa}zF-v_5#tXLDSgHVz|6$!OIygjuJ)!WPy~PeKWjQEtMjBc$ zpabVDc>%zvMz9l{Dqde~ZVw3!PdGKD|S?Kk{^ZKmB@9!?k573{$ zdy3}*!vgZQf-(Q1o+ECzew( z%l?_;{T}dr-i~ftUP!(OHQtRtFZ6yY{w?%gioGfd-mATsq4LRtdCB5LT;M&VWiei( z{-L^C8&ShU|K1Ze(9?;6?G0fY57^E(T5tCChKY47;5U3mwDoMZeGB3FS(%ag^N2Xr>q1OFR~vk!C}SJ-C|yjLCe)eGwiVBZDs{_^-UyMNXgZ!+z|BD9v~ zn?ITF6VpHjjsco1`Z;j$*@qn;YZlxEjQZ6Cd&$T7_8-0G0zUkbvp}!QabSUO&VtSc znT{vVEagF8n>TM6fam-3vHhP8o@IGogRd^=DCe4qZSrUT2K>hbv`JbD`oQ|S>gU08 z8-D{m3+%J&DVn<8rGWbzyOa<>^--FLadV1jyXyb>+##}#5r@kD<5`!_SyfTZzv_&oi@L3ha zMIR3?w*36Y<-xjFbsy!K_i!yTThT5K_A?%)&ZqxZ2A0Hbwi|qBrK8jY(dNgm$mpZQ zg$>3fF~4yeTMm8vWEcj4zD-+U%e1Z=eg&(itrO^?2tkBxMwWEF_z#h>&tSZ#5~a3$ z#(L8-e!>IbO9l(T9rB0pXmWd9taKkZ(^q-|S%0ga;5$GI_+S242Ie&$=md0=iBg@H z>GrablMq!N8i2?1zcMf<8Tb;c$|JOFn7BYd9x8Lg=ZSs#D+6fB062Szk9UD2Uv{s@ zD)Vpx{ulg}f$3!c?71wCQQ_J6=*+TE>n^$sf$<>hU##}83`{8lWnjFtcF~Ex%nAfJ z!sm;@e#jPUjQrb|189;G4%)^tW7U#?1MevV_%Z_iFU@+&$QQDQf4loaIj`X z0&Ga~{va7h2D==9ckXmO*9{@;9K6ae2!c+DX7HuYrZ4EXX(d{WOr9?HPHZjY}5 z`;2F-{t--D0wlx1xfOsHNDyJWh~=d7ZwK%=hN|&Sd#>6NkmHXmGD3?NtR3((0~=%b zoWifaP!3=l_ks{LUK?QNNdHGN;};_h>(JnK2jWlJb227tu-}VkARdTP=bw{5-Csg+5ms$8GtW~?XMWtN7jS+=o2uevjaA*Yk}M${*%P~&5?>#;X(i& zF#vw)fC&4p?+0-{;{^EpJ6M*ifNTjwsPq1DYqP((D2#$1uE|FP))n@E_G$xo846+% zi1i@C;|92&fX}ypf0uy>`?E0xQ8Y?J0Pnwm|6d$_q(Gz!Hv-sI;)6&Up}|W5t`wks zgWm#wbu>Sc>Tl{V1^!atF9rTm;18g{JRR($Kq3?09DyL>iRpF-LQG7*6 zFwawFN&^6q6Q6_h#3T&hr1THq0f2u@L#PSVgWvpD`Umg*(-iZ-1I;%B?RID5chz{b?-PQO}IMme{%f+;0OB*&;v0Z zM0jm=Ivwsu@XQlL!5H=5d%G;a0X}0#8`uoxf-CIfX*!&zx<3N+Sg;OL8LUD7R=O;p zo5cpv7{CteWv9YzuJ`f)4R`+HW{Xz!KnDr8Y1rm{t~kz?AGV#n3f9Dyr5+pTT`_^Y zo&_*2wM|zRuoIw1iy1#DQ=|$HA;3F&33xu8Otb>~InJMi-i+0NwK-ORcjZsSeVise zpihvR5x6CO2y9jk0=!#(0q)~8=mu@>*b<}pui`-;1n>1V0eH`MEp{CK#kj(DA`1Tk za*1vPs`6lh`e1vt<+P`%5BTX_lCyy(lJV9N4%k-j8ic#MuN z4Zyq|3zPxd$xSY2H2uu#$Z|pVUvNA&-8Uu70GBKfanPXw7(-l`4tMxIEMvof5leg>Zr)%We|vZ6tM zXB#TkKy*6U|9&6z10K`i4|tCU@I!0wMS1+vo##7O!oufx!sqzS#<#KOK<_;DnM&Zf z5}IX~jt9 znegy=?33$-&)x$CPFdXW-~c$E@8G}QnOp`M=^y+yfcyezyfbaRS$E9PKHqkzzZaF~ zcNvs5{n<7!kEaUo{Y5%w-en^H0q%Pjfaf4t6)4^`8Fk4m;ZIV0}yIg_)UkJ$OC4wY=DJYzZIu*`662l|2U zXGw!GKl==M=TsMbPU>`FHvHlK5S`H5@p++VunvJeBrC^d!22*eIlzB-p)|<3XFX$I zSdrj2EiK_QW#Kc=&<$`qSpdAfV7!Mvj(>~>57^&KbBuTS^QPIuP% zo(-KJ>CUYktjHmd!7`IK-M23h4zzV)~)e+i1w*7G#0N(^YQ0AP!1F$U4CDbH^{0sK7n7QdhGu+Pns|+;h zVL6WP-^IP2@Ke(#65&tw{a zcVHQqlb^cR?&foX9q#KU!xnEOiFO|f&k^Ty20hUKT$qgSRB13axH%cVnbIi^>T|+B zKfv){_`~IY%uPb8oT>Vcncy3HmJP-!T=hr@IIGLLN{a+O}Lx#The!{r%ZDFn^f= zPN3J=g@Sbh@ECtw4*=_#dcHKFDjxfxqIHF4e1EF40Y43kj zzSsZyl1O(HJTFW*yL&P4LB9+Q{v2?Y^nz^wU|InDV4pl__lFbd@r!=v z!!S?e<3fLfZ|7D}=I3985Bhuu{xATnGp=*ZmlmKOSKSBW0}L?7HUu<4 z%Z_9Yw8{iynw|gbIQ~@_qE|1#Yb~G!tV@OcN=}sBx%?gh{C*4G*980jzOU7x2f^~l z1z?Bw1_c6Ipe+vo=SJ{OFo@#77w5d@t;+-Zf1m)e3)@yng9z)@-hc?NGr+nPIM#v~ z4&oUQ*@0g|jDOzzZ~ltZrwhOZLkj#H6o7=Uz-0q``Nyxz zxU&aq*ku9;)??l%#{IA`fZE}}P&ayk#{HuZr~E&SJNb(I|9#9^u86Vc|GK7(y+8R{ zH+FyQiaUNCgKyl=$@rCF3?GqE@&JmCU9HEyWn=UJP9jnu5CC093j}l;EfCOcln{W9 zqXhxFj?)<~VAQt+a*Q7-WBdUHjC#BPFM{l&FTfX2(cW&=J^{c4+xDLT`ph_R zoo((4=2!gTAo3sGO8ZNZ2+`z*_h2c4SOel*#!zrxcrEV{;MXsiGl2076{tTEM6}is zK)&hlYXZ;qC~&R$DZGH!f`OcffI4A+9Mi!x*ZciIo{W7Iw=U_pE?AWpmKS{xmqJem z^YI$+;j$!tTEf(LSAg>Gg1At5nT5NE4;xy0N+B_2~NI1bgT%01w)GzaOdc!h5=5|LOmt z7i?o5rL_&M_^IgSgwf>Oe@?RFss%dTS=VnAxM<)tNqC>$4}BzTTi#lpi|Xt6GP*|# z-lH>H99iH#+&o{~$@F_13igc8BufBp*v1H+`~UE6uFs{p6L5iVWZg3T0fsS}8eiJC zaY_`xd>!5so;w+KIGuCfW`WSm?e)Rl?ooS@DPZXUFw#wh0LTlEBPZiLnof24Uv<|W z8$}Vuk0_F0RE&wle=I~Xs3B2aRYVGb7#|o+s(%n4)mlOTK}DkwOgKd#B0;JoMq|Jr zD6|S#3WP#S3k9KIp}blsr6+yxsHIRqX(_C~-`veHyEi+x+bdNk`EGV*znS^X?Cw0j z@4IpS03^tLbmKBD4&np;rB3{aqdZ2j8-D74HbK6)GaSoVJ9&gFeqj6yx^{P~bwJ$1 zAfs&E_AjOwbx7RmMjHavTh|!n?`7J?WBaZ3?>%e6F7BbdZ920Ef8f^kYW%@p7RjPK z`Awn2;kHD-Te@_PMI9lXYrWJAoipgmO&A&%djwCO+Wr_HzEg3Ut`9?Q#Y^9Kro6;j z_s&x`JUV$;>IFIZOyx)JT|k@PF6)4}Up=IWVxf#|W7Pp&Q(DxSrHl^sd7XLk9dtVC z9<9dnaq@ZyrzrS+=~y!FHRB(LOx0;89BbdQ&$L)LAE1n&&Q%p;TR9VlY10|%F;(Kn z`?J`-sm#b1@bQVZu&LtX6HgZHDku1d=p0p1*V zU-(G#7|1qncFV_$UV6S_b0lv@YCQPX=|emH;E$2-5IPFuk_+50tMP9ApbD~J)~iuG zlr3(#cuu_?b6vf4b(CK%OLJX={Sd9}DR>_N#mxVmd7Rq6J*Ip$f_m2*KOAGjQ&WU7drmzIXE~ZM-;Xrgi=zZSey%UqUvo6+Y%Qgltei=MdmZU|e znjVpd*>E<}g=-z3WhTpF~0 zcX|Sn08?gaKaSBEAYpY@P+_6lS7)QWAa0E!{ys zL~$heg%nSMAEdYvd;-HySd1wU2#YlZ0+$(|5(o&fr=&n2#4xm3gpXBJA;XFvWEdyE zS|2BoBHo8zi0mK$6)p$)iZJ{T<58~k1wP;sc!5*m7xe*tSucy}@Dr_fVWd5fk!T-e zB-#rZq>v8@E&5h4(!QajaF{J02yn3L1sV>D%4zjLpo1Lb8ML_di$vpk~zvFp$TAMntpv>N&M8|RBErb4< zFTGaO`$43u0r{=38~<+P<>^^~?;()$-FC~@Py8m#D~w|m%DorlNq&px0@UHB{W23Z zh03kp7QHWVX2QO-^HGa1<}94^>;nm2+V$g}NT@hROZBCN;UUJuufu-G%Q^rk*R}@n zYhT6$qdezZS%3OGYfe%zAdc@F=gU#PirmGfEIr@jem-q&sd?jirK9{sj{DZ887~^o z0wjReOD6l1*Q~N1KX;bR@D-3~1K85!-0F<8e1;EXWy)f-KF^70?||p0&V9GPn;I;g z-K1za8Oh?DD*H__hUqYhIPSyg?3OmyAGbEcwzbSpwMRvM59em<_zaM~kIci(=kufN zf^;X#ifw1QJdk36 zyaIL}jB_6+7S0(_9_@l8is7sF${gbxp`7l{c4FWdJKk9@zhUYRBOmV1_-Tg__=or{ z%Z(rJ1HX$jP`r6DbyVhKF4=)A-Rr23cXwbJ4}Sxw5k%Rv6QG~ae{t{hhVRo#G|-9c zf_iq9W0;Kh>sxI}*rMqMeKIJAg|`)`Qp>fM11f{dKnHKjc_^^6`qWcs#BjCZIz4=}|0SbZ^fX3qa zcA3b&d2u~FGDli3<7ul)I@+@ocp`S~IUkmM z@OPje=l8-kyay!K*POG^b~ojVh@bqMXYxOiGSsx}?|L(>bO;Xw@!e4Qbk|I){a-W0 zKM6W-$fE-H`p7bMKJN2BkIEc*us>V^@?=*CeB9f58uSq;9et=)2Akzy#%l2#_jkKt YuN5=LU`!8m9VPFPhrCR4IVBMI2c*&^hX4Qo literal 0 HcmV?d00001 From ee4d89e51cf7dc968119b682e5fe0229d74b5454 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Sun, 6 Mar 2022 17:42:03 +0100 Subject: [PATCH 02/34] App: allow to set debug mode by env --- app/Bootstrap.php | 2 +- docker-compose.yml | 3 ++- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/app/Bootstrap.php b/app/Bootstrap.php index cbb844f..082f4eb 100644 --- a/app/Bootstrap.php +++ b/app/Bootstrap.php @@ -11,7 +11,7 @@ public static function boot(): Configurator { $configurator = new Configurator(); - $configurator->setDebugMode(false); + $configurator->setDebugMode(getenv('NETTE_DEBUG') === '1'); $configurator->enableTracy(__DIR__ . '/../log'); $configurator->setTimeZone('Europe/Prague'); diff --git a/docker-compose.yml b/docker-compose.yml index c6ba3ba..08bf5e3 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -7,9 +7,10 @@ services: - ./:/srv ports: - 80:80 - depends_on: - database + environment: + NETTE_DEBUG: 1 database: image: mariadb:latest From 64707321095d91a0266352c0710081729005f8ca Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Sun, 6 Mar 2022 18:17:50 +0100 Subject: [PATCH 03/34] App: load assets from vendor folder (to match given version) --- app/Model/Parameters.php | 24 ++++++ app/{Router => Model}/RouterFactory.php | 4 +- app/Presenters/AssetsPresenter.php | 34 +++++++++ app/templates/@layout.inFrame.latte | 73 ------------------ app/templates/@layout.latte | 17 +++-- config/common.neon | 6 +- www/styles.inFrame.css | 98 ------------------------- 7 files changed, 76 insertions(+), 180 deletions(-) create mode 100644 app/Model/Parameters.php rename app/{Router => Model}/RouterFactory.php (65%) create mode 100644 app/Presenters/AssetsPresenter.php delete mode 100644 app/templates/@layout.inFrame.latte delete mode 100644 www/styles.inFrame.css diff --git a/app/Model/Parameters.php b/app/Model/Parameters.php new file mode 100644 index 0000000..cb8efe9 --- /dev/null +++ b/app/Model/Parameters.php @@ -0,0 +1,24 @@ +parameters = $parameters; + } + + public function get(string $key): mixed + { + return $this->parameters[$key]; + } + +} diff --git a/app/Router/RouterFactory.php b/app/Model/RouterFactory.php similarity index 65% rename from app/Router/RouterFactory.php rename to app/Model/RouterFactory.php index b1d23b9..03bb51a 100644 --- a/app/Router/RouterFactory.php +++ b/app/Model/RouterFactory.php @@ -1,6 +1,6 @@ addRoute('[/]', 'Basic:default'); + $router->addRoute('_datagrid/css/', 'Assets:css'); + $router->addRoute('_datagrid/js/', 'Assets:js'); return $router; } diff --git a/app/Presenters/AssetsPresenter.php b/app/Presenters/AssetsPresenter.php new file mode 100644 index 0000000..17ca8b9 --- /dev/null +++ b/app/Presenters/AssetsPresenter.php @@ -0,0 +1,34 @@ +sendResponse(new CallbackResponse(function (IRequest $request, IResponse $response) use ($file): void { + $response->addHeader('content-type', 'text/css; charset=utf-8'); + echo FileSystem::read($this->parameters->get('vendorDir') . '/ublaboo/datagrid/assets/' . $file); + })); + } + + public function actionJs(string $file): void + { + $this->sendResponse(new CallbackResponse(function (IRequest $request, IResponse $response) use ($file): void { + $response->addHeader('content-type', 'application/javascript; charset=utf-8'); + echo FileSystem::read($this->parameters->get('vendorDir') . '/ublaboo/datagrid/assets/' . $file); + })); + } + +} diff --git a/app/templates/@layout.inFrame.latte b/app/templates/@layout.inFrame.latte deleted file mode 100644 index 2d10ebe..0000000 --- a/app/templates/@layout.inFrame.latte +++ /dev/null @@ -1,73 +0,0 @@ - - - - - - - {ifset title}{include title|stripHtml} | {/ifset}DataGrid Sandbox - - - - - - - - - - - - - - - - - - - - - - {snippet flashes} - {if count($flashes) != 0} -

-
- {$flash->message} -
-
- {/if} - {/snippet} - -
-
- {include content} -
-
- - {block scripts} - - - - - - - - - - - - - - - - - - - - - - - - - - {/block} - - diff --git a/app/templates/@layout.latte b/app/templates/@layout.latte index d0028ea..e010109 100644 --- a/app/templates/@layout.latte +++ b/app/templates/@layout.latte @@ -9,19 +9,21 @@ {ifset title}{include title|stripHtml} | {/ifset}DataGrid Sandbox - + - + - + - + + + @@ -94,18 +96,19 @@ --> - + - + - + + {/block} diff --git a/config/common.neon b/config/common.neon index b699cf0..8024ac3 100644 --- a/config/common.neon +++ b/config/common.neon @@ -4,7 +4,8 @@ application: *: App\*Module\Presenters\*Presenter services: - router: App\Router\RouterFactory::create + router: App\Model\RouterFactory::create + parameters: App\Model\Parameters(%parameters%) extensions: dibi: Dibi\Bridges\Nette\DibiExtension22 @@ -22,3 +23,6 @@ dibi: session: savePath: "%tempDir%/sessions" + +parameters: + vendorDir: %appDir%/../vendor diff --git a/www/styles.inFrame.css b/www/styles.inFrame.css deleted file mode 100644 index 9193f17..0000000 --- a/www/styles.inFrame.css +++ /dev/null @@ -1,98 +0,0 @@ -html, -body { - margin: 0; - padding: 0; - width: 100%; - height: 100%; -} - -body { - background-color: #f8f9fa; - text-align: center; -} - -.example { - background: #fff; - text-align: left; - border-radius: 2px; - display: inline-block; - height: auto; - width: 100%; - margin: 0; - position: relative; - box-shadow: 0 3px 6px rgba(0, 0, 0, 0.16), 0 3px 6px rgba(0, 0, 0, 0.23); - font-size: 0.9rem; - font-weight: 200; -} - -.flash { - position: fixed; - top: 0; - left: 0; - width: 100%; - height: 56px; - line-height: 56px; - box-shadow: 0 1px 3px rgba(0, 0, 0, .12), 0 1px 2px rgba(0, 0, 0, .24); - z-index: 1; - margin: 0; - padding: 0; - vertical-align: middle; - box-sizing: border-box; - transform: translateY(-56px) -} - -.flash.slide { - animation-name: flashes; - animation-duration: 4s; - animation-delay: 0; - animation-iteration-count: 1; - animation-direction: normal; -} - -@keyframes flashes { - - 0%, - 100% { - transform: translateY(-56px) - } - - 15%, - 85% { - transform: translateY(0) - } -} - -@-webkit-keyframes flashes { - - 0%, - 100% { - transform: translateY(-56px) - } - - 15%, - 85% { - transform: translateY(0) - } -} - -.item-detail-content { - padding: 1em 0; -} - -.row-item-detail td { - text-align: center; - background-color: #fff; -} - -.row-item-detail p { - text-align: left; -} - -.row-item-detail td .item-detail-content { - position: relative -} - -.row-item-detail td .item-detail-content small { - position: absolute; - right: 1em; -} From 3a757d568694bacf8f868d61ffba93061fe4da18 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Sun, 6 Mar 2022 17:42:39 +0100 Subject: [PATCH 04/34] Bootstrap 5 --- app/Presenters/ActionsPresenter.php | 2 +- app/Presenters/AddPresenter.php | 2 +- app/Presenters/EditPresenter.php | 2 +- app/Presenters/ExportPresenter.php | 2 +- app/Presenters/GroupActionsPresenter.php | 2 +- app/Presenters/RowPresenter.php | 2 +- 6 files changed, 6 insertions(+), 6 deletions(-) diff --git a/app/Presenters/ActionsPresenter.php b/app/Presenters/ActionsPresenter.php index 818958e..27ccbbf 100644 --- a/app/Presenters/ActionsPresenter.php +++ b/app/Presenters/ActionsPresenter.php @@ -22,7 +22,7 @@ public function createComponentGrid(): DataGrid $grid->setSortable(); $grid->addColumnNumber('id', 'Id') - ->setAlign('left') + ->setAlign('start') ->setSortable(); $grid->addColumnText('name', 'Name') diff --git a/app/Presenters/AddPresenter.php b/app/Presenters/AddPresenter.php index e99119b..f476032 100644 --- a/app/Presenters/AddPresenter.php +++ b/app/Presenters/AddPresenter.php @@ -19,7 +19,7 @@ public function createComponentGrid(): DataGrid $grid->setItemsPerPageList([20, 50, 100]); $grid->addColumnNumber('id', 'Id') - ->setAlign('left') + ->setAlign('start') ->setFilterText(); $grid->addColumnText('name', 'Name') diff --git a/app/Presenters/EditPresenter.php b/app/Presenters/EditPresenter.php index 27e51f8..0388be1 100644 --- a/app/Presenters/EditPresenter.php +++ b/app/Presenters/EditPresenter.php @@ -23,7 +23,7 @@ public function createComponentGrid(): DataGrid $grid->addColumnNumber('id', 'Id') ->setSortable() - ->setAlign('left'); + ->setAlign('start'); $grid->addColumnText('name', 'Name') ->setSortable() diff --git a/app/Presenters/ExportPresenter.php b/app/Presenters/ExportPresenter.php index 8ce5db8..6c1220f 100644 --- a/app/Presenters/ExportPresenter.php +++ b/app/Presenters/ExportPresenter.php @@ -20,7 +20,7 @@ public function createComponentGrid(): DataGrid $grid->setItemsPerPageList([20, 50, 100]); $grid->addColumnNumber('id', 'Id') - ->setAlign('left') + ->setAlign('start') ->setSortable(); $grid->addColumnText('name', 'Name') diff --git a/app/Presenters/GroupActionsPresenter.php b/app/Presenters/GroupActionsPresenter.php index ee72020..b817fdf 100644 --- a/app/Presenters/GroupActionsPresenter.php +++ b/app/Presenters/GroupActionsPresenter.php @@ -19,7 +19,7 @@ public function createComponentGrid(): DataGrid $grid->setItemsPerPageList([20, 50, 100]); $grid->addColumnNumber('id', 'Id') - ->setAlign('left') + ->setAlign('start') ->setSortable(); $grid->addColumnText('name', 'Name') diff --git a/app/Presenters/RowPresenter.php b/app/Presenters/RowPresenter.php index 87e6c3f..f67e5c0 100644 --- a/app/Presenters/RowPresenter.php +++ b/app/Presenters/RowPresenter.php @@ -24,7 +24,7 @@ public function createComponentGrid(): DataGrid }); $grid->addColumnNumber('id', 'Id') - ->setAlign('left') + ->setAlign('start') ->setSortable(); $grid->addColumnText('name', 'Name') From 63cf8ef9d53ccc8c72b2556155760e9e7a3397c9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Tue, 24 Jan 2023 11:41:40 +0100 Subject: [PATCH 05/34] Composer: upgrade deps, use datagrid:dev-next --- composer.json | 42 ++++++++++++++++++++++-------------------- 1 file changed, 22 insertions(+), 20 deletions(-) diff --git a/composer.json b/composer.json index 3be25a0..0808bff 100644 --- a/composer.json +++ b/composer.json @@ -14,28 +14,30 @@ "type": "project", "require": { "php": ">= 8.0", - "nette/application": "~3.1.0", - "nette/bootstrap": "~3.2.0", - "nette/caching": "~3.2.0", - "nette/database": "~3.1.0", - "nette/di": "^3.0", - "nette/finder": "~2.6.0", - "nette/forms": "~3.1.0", - "nette/http": "~3.2.0", - "nette/mail": "~3.1.0", - "nette/security": "~3.1.0", - "nette/utils": "^3.0", - "latte/latte": "^3.0", - "tracy/tracy": "^2.7.0", - "ublaboo/datagrid": "^6.0", - "dibi/dibi": "^5.0.0" + + "nette/application": "^3.1.0", + "nette/bootstrap": "^3.2.0", + "nette/caching": "^3.2.0", + "nette/database": "^3.1.0", + "nette/di": "^3.0.15", + "nette/forms": "^3.1.0", + "nette/http": "^3.2.0", + "nette/utils": "^3.2.0", + + "latte/latte": "^3.0.3", + "tracy/tracy": "^2.9.5", + + "ublaboo/datagrid": "dev-next", + + "nextras/orm": "^4.0.6", + "dibi/dibi": "^4.2.7" }, "require-dev": { - "ninjify/qa": "^0.13", - "phpstan/phpstan": "^1.0.0", - "phpstan/phpstan-dibi": "^1.0.0", - "phpstan/phpstan-nette": "^1.0.0", - "phpstan/phpstan-strict-rules": "^1.0.0" + "contributte/qa": "^0.4.0", + "phpstan/phpstan": "^1.9.14", + "phpstan/phpstan-dibi": "^1.0.1", + "phpstan/phpstan-nette": "^1.2.1", + "phpstan/phpstan-strict-rules": "^1.4.5" }, "autoload": { "psr-4": { From e82c31e3a8709a8432871248bc899f4fac68852e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Tue, 24 Jan 2023 11:41:49 +0100 Subject: [PATCH 06/34] NPM: init --- .gitignore | 6 +- package-lock.json | 770 ++++++++++++++++++++++++++++++++++++++++++++++ package.json | 22 ++ 3 files changed, 796 insertions(+), 2 deletions(-) create mode 100644 package-lock.json create mode 100644 package.json diff --git a/.gitignore b/.gitignore index a38efc3..db7c641 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,5 @@ -/_data +# Composer /vendor -/ftp-deployment + +# Node +/node_modules diff --git a/package-lock.json b/package-lock.json new file mode 100644 index 0000000..ac92bb1 --- /dev/null +++ b/package-lock.json @@ -0,0 +1,770 @@ +{ + "name": "datagrid", + "version": "0.0.0", + "lockfileVersion": 3, + "requires": true, + "packages": { + "": { + "name": "datagrid", + "version": "0.0.0", + "license": "MIT", + "dependencies": { + "@fortawesome/fontawesome-free": "^6.1.2", + "naja": "^2.2.0", + "nette-forms": "^3.0.0" + }, + "devDependencies": { + "autoprefixer": "^10.4.0", + "vite": "^2.6.10" + }, + "engines": { + "node": ">=17", + "npm": ">=8.10" + } + }, + "node_modules/@babel/runtime": { + "version": "7.20.13", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.20.13.tgz", + "integrity": "sha512-gt3PKXs0DBoL9xCvOIIZ2NEqAGZqHjAnmVbfQtB620V0uReIQutpel14KcneZuer7UioY8ALKZ7iocavvzTNFA==", + "dependencies": { + "regenerator-runtime": "^0.13.11" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@esbuild/linux-loong64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.14.54.tgz", + "integrity": "sha512-bZBrLAIX1kpWelV0XemxBZllyRmM6vgFQQG2GdNb+r3Fkp0FOh1NJSvekXDs7jq70k4euu1cryLMfU+mTXlEpw==", + "cpu": [ + "loong64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@fortawesome/fontawesome-free": { + "version": "6.2.1", + "resolved": "https://registry.npmjs.org/@fortawesome/fontawesome-free/-/fontawesome-free-6.2.1.tgz", + "integrity": "sha512-viouXhegu/TjkvYQoiRZK3aax69dGXxgEjpvZW81wIJdxm5Fnvp3VVIP4VHKqX4SvFw6qpmkILkD4RJWAdrt7A==", + "hasInstallScript": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/autoprefixer": { + "version": "10.4.13", + "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.13.tgz", + "integrity": "sha512-49vKpMqcZYsJjwotvt4+h/BCjJVnhGwcLpDt5xkcaOG3eLrG/HUYLagrihYsQ+qrIBgIzX1Rw7a6L8I/ZA1Atg==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/postcss/" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/autoprefixer" + } + ], + "dependencies": { + "browserslist": "^4.21.4", + "caniuse-lite": "^1.0.30001426", + "fraction.js": "^4.2.0", + "normalize-range": "^0.1.2", + "picocolors": "^1.0.0", + "postcss-value-parser": "^4.2.0" + }, + "bin": { + "autoprefixer": "bin/autoprefixer" + }, + "engines": { + "node": "^10 || ^12 || >=14" + }, + "peerDependencies": { + "postcss": "^8.1.0" + } + }, + "node_modules/browserslist": { + "version": "4.21.4", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.21.4.tgz", + "integrity": "sha512-CBHJJdDmgjl3daYjN5Cp5kbTf1mUhZoS+beLklHIvkOWscs83YAhLlF3Wsh/lciQYAcbBJgTOD44VtG31ZM4Hw==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/browserslist" + } + ], + "dependencies": { + "caniuse-lite": "^1.0.30001400", + "electron-to-chromium": "^1.4.251", + "node-releases": "^2.0.6", + "update-browserslist-db": "^1.0.9" + }, + "bin": { + "browserslist": "cli.js" + }, + "engines": { + "node": "^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7" + } + }, + "node_modules/caniuse-lite": { + "version": "1.0.30001447", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001447.tgz", + "integrity": "sha512-bdKU1BQDPeEXe9A39xJnGtY0uRq/z5osrnXUw0TcK+EYno45Y+U7QU9HhHEyzvMDffpYadFXi3idnSNkcwLkTw==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/caniuse-lite" + } + ] + }, + "node_modules/electron-to-chromium": { + "version": "1.4.284", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.284.tgz", + "integrity": "sha512-M8WEXFuKXMYMVr45fo8mq0wUrrJHheiKZf6BArTKk9ZBYCKJEOU5H8cdWgDT+qCVZf7Na4lVUaZsA+h6uA9+PA==", + "dev": true + }, + "node_modules/esbuild": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.14.54.tgz", + "integrity": "sha512-Cy9llcy8DvET5uznocPyqL3BFRrFXSVqbgpMJ9Wz8oVjZlh/zUSNbPRbov0VX7VxN2JH1Oa0uNxZ7eLRb62pJA==", + "dev": true, + "hasInstallScript": true, + "bin": { + "esbuild": "bin/esbuild" + }, + "engines": { + "node": ">=12" + }, + "optionalDependencies": { + "@esbuild/linux-loong64": "0.14.54", + "esbuild-android-64": "0.14.54", + "esbuild-android-arm64": "0.14.54", + "esbuild-darwin-64": "0.14.54", + "esbuild-darwin-arm64": "0.14.54", + "esbuild-freebsd-64": "0.14.54", + "esbuild-freebsd-arm64": "0.14.54", + "esbuild-linux-32": "0.14.54", + "esbuild-linux-64": "0.14.54", + "esbuild-linux-arm": "0.14.54", + "esbuild-linux-arm64": "0.14.54", + "esbuild-linux-mips64le": "0.14.54", + "esbuild-linux-ppc64le": "0.14.54", + "esbuild-linux-riscv64": "0.14.54", + "esbuild-linux-s390x": "0.14.54", + "esbuild-netbsd-64": "0.14.54", + "esbuild-openbsd-64": "0.14.54", + "esbuild-sunos-64": "0.14.54", + "esbuild-windows-32": "0.14.54", + "esbuild-windows-64": "0.14.54", + "esbuild-windows-arm64": "0.14.54" + } + }, + "node_modules/esbuild-android-64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-android-64/-/esbuild-android-64-0.14.54.tgz", + "integrity": "sha512-Tz2++Aqqz0rJ7kYBfz+iqyE3QMycD4vk7LBRyWaAVFgFtQ/O8EJOnVmTOiDWYZ/uYzB4kvP+bqejYdVKzE5lAQ==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-android-arm64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-android-arm64/-/esbuild-android-arm64-0.14.54.tgz", + "integrity": "sha512-F9E+/QDi9sSkLaClO8SOV6etqPd+5DgJje1F9lOWoNncDdOBL2YF59IhsWATSt0TLZbYCf3pNlTHvVV5VfHdvg==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-darwin-64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-darwin-64/-/esbuild-darwin-64-0.14.54.tgz", + "integrity": "sha512-jtdKWV3nBviOd5v4hOpkVmpxsBy90CGzebpbO9beiqUYVMBtSc0AL9zGftFuBon7PNDcdvNCEuQqw2x0wP9yug==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-darwin-arm64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-darwin-arm64/-/esbuild-darwin-arm64-0.14.54.tgz", + "integrity": "sha512-OPafJHD2oUPyvJMrsCvDGkRrVCar5aVyHfWGQzY1dWnzErjrDuSETxwA2HSsyg2jORLY8yBfzc1MIpUkXlctmw==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-freebsd-64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-freebsd-64/-/esbuild-freebsd-64-0.14.54.tgz", + "integrity": "sha512-OKwd4gmwHqOTp4mOGZKe/XUlbDJ4Q9TjX0hMPIDBUWWu/kwhBAudJdBoxnjNf9ocIB6GN6CPowYpR/hRCbSYAg==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-freebsd-arm64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-freebsd-arm64/-/esbuild-freebsd-arm64-0.14.54.tgz", + "integrity": "sha512-sFwueGr7OvIFiQT6WeG0jRLjkjdqWWSrfbVwZp8iMP+8UHEHRBvlaxL6IuKNDwAozNUmbb8nIMXa7oAOARGs1Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-linux-32": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-linux-32/-/esbuild-linux-32-0.14.54.tgz", + "integrity": "sha512-1ZuY+JDI//WmklKlBgJnglpUL1owm2OX+8E1syCD6UAxcMM/XoWd76OHSjl/0MR0LisSAXDqgjT3uJqT67O3qw==", + "cpu": [ + "ia32" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-linux-64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-linux-64/-/esbuild-linux-64-0.14.54.tgz", + "integrity": "sha512-EgjAgH5HwTbtNsTqQOXWApBaPVdDn7XcK+/PtJwZLT1UmpLoznPd8c5CxqsH2dQK3j05YsB3L17T8vE7cp4cCg==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-linux-arm": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-linux-arm/-/esbuild-linux-arm-0.14.54.tgz", + "integrity": "sha512-qqz/SjemQhVMTnvcLGoLOdFpCYbz4v4fUo+TfsWG+1aOu70/80RV6bgNpR2JCrppV2moUQkww+6bWxXRL9YMGw==", + "cpu": [ + "arm" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-linux-arm64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-linux-arm64/-/esbuild-linux-arm64-0.14.54.tgz", + "integrity": "sha512-WL71L+0Rwv+Gv/HTmxTEmpv0UgmxYa5ftZILVi2QmZBgX3q7+tDeOQNqGtdXSdsL8TQi1vIaVFHUPDe0O0kdig==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-linux-mips64le": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-linux-mips64le/-/esbuild-linux-mips64le-0.14.54.tgz", + "integrity": "sha512-qTHGQB8D1etd0u1+sB6p0ikLKRVuCWhYQhAHRPkO+OF3I/iSlTKNNS0Lh2Oc0g0UFGguaFZZiPJdJey3AGpAlw==", + "cpu": [ + "mips64el" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-linux-ppc64le": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-linux-ppc64le/-/esbuild-linux-ppc64le-0.14.54.tgz", + "integrity": "sha512-j3OMlzHiqwZBDPRCDFKcx595XVfOfOnv68Ax3U4UKZ3MTYQB5Yz3X1mn5GnodEVYzhtZgxEBidLWeIs8FDSfrQ==", + "cpu": [ + "ppc64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-linux-riscv64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-linux-riscv64/-/esbuild-linux-riscv64-0.14.54.tgz", + "integrity": "sha512-y7Vt7Wl9dkOGZjxQZnDAqqn+XOqFD7IMWiewY5SPlNlzMX39ocPQlOaoxvT4FllA5viyV26/QzHtvTjVNOxHZg==", + "cpu": [ + "riscv64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-linux-s390x": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-linux-s390x/-/esbuild-linux-s390x-0.14.54.tgz", + "integrity": "sha512-zaHpW9dziAsi7lRcyV4r8dhfG1qBidQWUXweUjnw+lliChJqQr+6XD71K41oEIC3Mx1KStovEmlzm+MkGZHnHA==", + "cpu": [ + "s390x" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-netbsd-64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-netbsd-64/-/esbuild-netbsd-64-0.14.54.tgz", + "integrity": "sha512-PR01lmIMnfJTgeU9VJTDY9ZerDWVFIUzAtJuDHwwceppW7cQWjBBqP48NdeRtoP04/AtO9a7w3viI+PIDr6d+w==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-openbsd-64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-openbsd-64/-/esbuild-openbsd-64-0.14.54.tgz", + "integrity": "sha512-Qyk7ikT2o7Wu76UsvvDS5q0amJvmRzDyVlL0qf5VLsLchjCa1+IAvd8kTBgUxD7VBUUVgItLkk609ZHUc1oCaw==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-sunos-64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-sunos-64/-/esbuild-sunos-64-0.14.54.tgz", + "integrity": "sha512-28GZ24KmMSeKi5ueWzMcco6EBHStL3B6ubM7M51RmPwXQGLe0teBGJocmWhgwccA1GeFXqxzILIxXpHbl9Q/Kw==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "sunos" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-windows-32": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-windows-32/-/esbuild-windows-32-0.14.54.tgz", + "integrity": "sha512-T+rdZW19ql9MjS7pixmZYVObd9G7kcaZo+sETqNH4RCkuuYSuv9AGHUVnPoP9hhuE1WM1ZimHz1CIBHBboLU7w==", + "cpu": [ + "ia32" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-windows-64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-windows-64/-/esbuild-windows-64-0.14.54.tgz", + "integrity": "sha512-AoHTRBUuYwXtZhjXZbA1pGfTo8cJo3vZIcWGLiUcTNgHpJJMC1rVA44ZereBHMJtotyN71S8Qw0npiCIkW96cQ==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/esbuild-windows-arm64": { + "version": "0.14.54", + "resolved": "https://registry.npmjs.org/esbuild-windows-arm64/-/esbuild-windows-arm64-0.14.54.tgz", + "integrity": "sha512-M0kuUvXhot1zOISQGXwWn6YtS+Y/1RT9WrVIOywZnJHo3jCDyewAc79aKNQWFCQm+xNHVTq9h8dZKvygoXQQRg==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/escalade": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", + "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/fraction.js": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/fraction.js/-/fraction.js-4.2.0.tgz", + "integrity": "sha512-MhLuK+2gUcnZe8ZHlaaINnQLl0xRIGRfcGk2yl8xoQAfHrSsL3rYu6FCmBdkdbhc9EPlwyGHewaRsvwRMJtAlA==", + "dev": true, + "engines": { + "node": "*" + }, + "funding": { + "type": "patreon", + "url": "https://www.patreon.com/infusion" + } + }, + "node_modules/fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "dev": true, + "hasInstallScript": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, + "node_modules/function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", + "dev": true + }, + "node_modules/has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.1" + }, + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/is-core-module": { + "version": "2.11.0", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.11.0.tgz", + "integrity": "sha512-RRjxlvLDkD1YJwDbroBHMb+cukurkDWNyHx7D3oNB5x9rb5ogcksMC5wHCadcXoo67gVr/+3GFySh3134zi6rw==", + "dev": true, + "dependencies": { + "has": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/naja": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/naja/-/naja-2.5.0.tgz", + "integrity": "sha512-SmGR5VVVtF7jF6EPRkPx+cuhzsxDvKKbs+XO8RO2/2En2l2PBe9LglwFBbYIWMLxeGuYl5wGt2MQvkUjjVaagg==", + "dependencies": { + "@babel/runtime": "^7.18.3" + } + }, + "node_modules/nanoid": { + "version": "3.3.4", + "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.4.tgz", + "integrity": "sha512-MqBkQh/OHTS2egovRtLk45wEyNXwF+cokD+1YPf9u5VfJiRdAiRwB2froX5Co9Rh20xs4siNPm8naNotSD6RBw==", + "dev": true, + "bin": { + "nanoid": "bin/nanoid.cjs" + }, + "engines": { + "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" + } + }, + "node_modules/nette-forms": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/nette-forms/-/nette-forms-3.3.1.tgz", + "integrity": "sha512-UOmA3rF+FjpSci5CGmMtsy79PMWCcl0yyfyCd8YXVS+c68FAnVq3ref5qSxYFcwFynTqcPsYKhsNh8eYW5nVhQ==" + }, + "node_modules/node-releases": { + "version": "2.0.8", + "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.8.tgz", + "integrity": "sha512-dFSmB8fFHEH/s81Xi+Y/15DQY6VHW81nXRj86EMSL3lmuTmK1e+aT4wrFCkTbm+gSwkw4KpX+rT/pMM2c1mF+A==", + "dev": true + }, + "node_modules/normalize-range": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/normalize-range/-/normalize-range-0.1.2.tgz", + "integrity": "sha512-bdok/XvKII3nUpklnV6P2hxtMNrCboOjAcyBuQnWEhO665FwrSNRxU+AqpsyvO6LgGYPspN+lu5CLtw4jPRKNA==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/path-parse": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", + "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", + "dev": true + }, + "node_modules/picocolors": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.0.0.tgz", + "integrity": "sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==", + "dev": true + }, + "node_modules/postcss": { + "version": "8.4.21", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.21.tgz", + "integrity": "sha512-tP7u/Sn/dVxK2NnruI4H9BG+x+Wxz6oeZ1cJ8P6G/PZY0IKk4k/63TDsQf2kQq3+qoJeLm2kIBUNlZe3zgb4Zg==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/postcss/" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/postcss" + } + ], + "dependencies": { + "nanoid": "^3.3.4", + "picocolors": "^1.0.0", + "source-map-js": "^1.0.2" + }, + "engines": { + "node": "^10 || ^12 || >=14" + } + }, + "node_modules/postcss-value-parser": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/postcss-value-parser/-/postcss-value-parser-4.2.0.tgz", + "integrity": "sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ==", + "dev": true + }, + "node_modules/regenerator-runtime": { + "version": "0.13.11", + "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.11.tgz", + "integrity": "sha512-kY1AZVr2Ra+t+piVaJ4gxaFaReZVH40AKNo7UCX6W+dEwBo/2oZJzqfuN1qLq1oL45o56cPaTXELwrTh8Fpggg==" + }, + "node_modules/resolve": { + "version": "1.22.1", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.1.tgz", + "integrity": "sha512-nBpuuYuY5jFsli/JIs1oldw6fOQCBioohqWZg/2hiaOybXOft4lonv85uDOKXdf8rhyK159cxU5cDcK/NKk8zw==", + "dev": true, + "dependencies": { + "is-core-module": "^2.9.0", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + }, + "bin": { + "resolve": "bin/resolve" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/rollup": { + "version": "2.77.3", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-2.77.3.tgz", + "integrity": "sha512-/qxNTG7FbmefJWoeeYJFbHehJ2HNWnjkAFRKzWN/45eNBBF/r8lo992CwcJXEzyVxs5FmfId+vTSTQDb+bxA+g==", + "dev": true, + "bin": { + "rollup": "dist/bin/rollup" + }, + "engines": { + "node": ">=10.0.0" + }, + "optionalDependencies": { + "fsevents": "~2.3.2" + } + }, + "node_modules/source-map-js": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.0.2.tgz", + "integrity": "sha512-R0XvVJ9WusLiqTCEiGCmICCMplcCkIwwR11mOSD9CR5u+IXYdiseeEuXCVAjS54zqwkLcPNnmU4OeJ6tUrWhDw==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/supports-preserve-symlinks-flag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", + "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/update-browserslist-db": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.0.10.tgz", + "integrity": "sha512-OztqDenkfFkbSG+tRxBeAnCVPckDBcvibKd35yDONx6OU8N7sqgwc7rCbkJ/WcYtVRZ4ba68d6byhC21GFh7sQ==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/browserslist" + } + ], + "dependencies": { + "escalade": "^3.1.1", + "picocolors": "^1.0.0" + }, + "bin": { + "browserslist-lint": "cli.js" + }, + "peerDependencies": { + "browserslist": ">= 4.21.0" + } + }, + "node_modules/vite": { + "version": "2.9.15", + "resolved": "https://registry.npmjs.org/vite/-/vite-2.9.15.tgz", + "integrity": "sha512-fzMt2jK4vQ3yK56te3Kqpkaeq9DkcZfBbzHwYpobasvgYmP2SoAr6Aic05CsB4CzCZbsDv4sujX3pkEGhLabVQ==", + "dev": true, + "dependencies": { + "esbuild": "^0.14.27", + "postcss": "^8.4.13", + "resolve": "^1.22.0", + "rollup": ">=2.59.0 <2.78.0" + }, + "bin": { + "vite": "bin/vite.js" + }, + "engines": { + "node": ">=12.2.0" + }, + "optionalDependencies": { + "fsevents": "~2.3.2" + }, + "peerDependencies": { + "less": "*", + "sass": "*", + "stylus": "*" + }, + "peerDependenciesMeta": { + "less": { + "optional": true + }, + "sass": { + "optional": true + }, + "stylus": { + "optional": true + } + } + } + } +} diff --git a/package.json b/package.json new file mode 100644 index 0000000..788cf5f --- /dev/null +++ b/package.json @@ -0,0 +1,22 @@ +{ + "name": "datagrid", + "version": "0.0.0", + "license": "MIT", + "engines": { + "npm": ">=8.10", + "node": ">=17" + }, + "dependencies": { + "@fortawesome/fontawesome-free": "^6.1.2", + "naja": "^2.2.0", + "nette-forms": "^3.0.0" + }, + "devDependencies": { + "autoprefixer": "^10.4.0", + "vite": "^2.6.10" + }, + "scripts": { + "watch": "vite build --watch --mode=development", + "build": "vite build --mode=production" + } +} From 07a832d856849a601660ad649371b00bc5d19003 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Tue, 24 Jan 2023 11:42:01 +0100 Subject: [PATCH 07/34] Codesniffer: use contributte/qa --- ruleset.xml | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/ruleset.xml b/ruleset.xml index b146dae..7ab6433 100644 --- a/ruleset.xml +++ b/ruleset.xml @@ -1,15 +1,14 @@ - - - + + From 25bc996b0ca554b7b199b7d5731cf67c1cda9178 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Tue, 24 Jan 2023 11:42:09 +0100 Subject: [PATCH 08/34] Build: init vite --- vite.config.js | 43 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 43 insertions(+) create mode 100644 vite.config.js diff --git a/vite.config.js b/vite.config.js new file mode 100644 index 0000000..c7700a8 --- /dev/null +++ b/vite.config.js @@ -0,0 +1,43 @@ +import { defineConfig } from 'vite'; +import { resolve } from 'path'; + +export default defineConfig(({ mode }) => { + const DEV = mode === 'development'; + + return { + publicDir: './public/static', + resolve: { + alias: { + '@': resolve(__dirname, 'assets/js'), + '~': resolve(__dirname, 'node_modules'), + }, + }, + base: '/dist/', + server: { + open: false, + hmr: false, + }, + css: { + postcss: [ + "autoprefixer" + ] + }, + build: { + manifest: true, + outDir: './public/dist/', + emptyOutDir: false, + minify: DEV ? false : 'esbuild', + rollupOptions: { + output: { + manualChunks: undefined, + chunkFileNames: DEV ? '[name].js' : '[name]-[hash].js', + entryFileNames: DEV ? '[name].js' : '[name].[hash].js', + assetFileNames: DEV ? '[name].[ext]' : '[name].[hash].[ext]', + }, + input: { + app: './assets/js/app.js' + } + } + }, + } +}); From bdbcad37b20e679e2eaf3ef37cf78ee42be23f5b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Tue, 24 Jan 2023 11:49:15 +0100 Subject: [PATCH 09/34] Phpstan: deprecation rules --- app/Bootstrap.php | 2 +- app/Presenters/AbstractPresenter.php | 8 +------- composer.json | 3 ++- phpstan.neon | 4 +++- 4 files changed, 7 insertions(+), 10 deletions(-) diff --git a/app/Bootstrap.php b/app/Bootstrap.php index 082f4eb..2494eea 100644 --- a/app/Bootstrap.php +++ b/app/Bootstrap.php @@ -2,7 +2,7 @@ namespace App; -use Nette\Configurator; +use Nette\Bootstrap\Configurator; final class Bootstrap { diff --git a/app/Presenters/AbstractPresenter.php b/app/Presenters/AbstractPresenter.php index 336be33..ed71e3a 100644 --- a/app/Presenters/AbstractPresenter.php +++ b/app/Presenters/AbstractPresenter.php @@ -6,7 +6,6 @@ use Nette\Application\UI\Presenter; use Nette\DI\Attributes\Inject; use Ublaboo\DataGrid\DataGrid; -use UnexpectedValueException; abstract class AbstractPresenter extends Presenter { @@ -16,7 +15,6 @@ abstract class AbstractPresenter extends Presenter abstract public function createComponentGrid(): DataGrid; - /** * @param mixed $id */ @@ -33,11 +31,7 @@ public function changeStatus($id, string $newStatus): void } if ($this->isAjax()) { - $grid = $this['grid']; - - if (!$grid instanceof DataGrid) { - throw new UnexpectedValueException(); - } + $grid = $this->getComponent('grid'); $grid->redrawItem($id); $this->flashMessage('Status changed'); diff --git a/composer.json b/composer.json index 0808bff..6d3b0b6 100644 --- a/composer.json +++ b/composer.json @@ -37,7 +37,8 @@ "phpstan/phpstan": "^1.9.14", "phpstan/phpstan-dibi": "^1.0.1", "phpstan/phpstan-nette": "^1.2.1", - "phpstan/phpstan-strict-rules": "^1.4.5" + "phpstan/phpstan-strict-rules": "^1.4.5", + "phpstan/phpstan-deprecation-rules": "^1.1.1" }, "autoload": { "psr-4": { diff --git a/phpstan.neon b/phpstan.neon index 52cbae7..7c5cbd9 100644 --- a/phpstan.neon +++ b/phpstan.neon @@ -1,7 +1,9 @@ includes: - - vendor/phpstan/phpstan-dibi/extension.neon + - vendor/phpstan/phpstan-deprecation-rules/rules.neon - vendor/phpstan/phpstan-nette/extension.neon - vendor/phpstan/phpstan-nette/rules.neon + - vendor/phpstan/phpstan-strict-rules/rules.neon + - vendor/phpstan/phpstan-dibi/extension.neon parameters: level: 8 From 06f4266002a24d3443a4f98c8e2a095308260e5a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Tue, 24 Jan 2023 11:49:56 +0100 Subject: [PATCH 10/34] Codesniffer: fixes --- Makefile | 10 +++++++--- app/Presenters/AbstractPresenter.php | 5 +---- app/Presenters/ActionsPresenter.php | 3 --- app/Presenters/BasicPresenter.php | 4 +--- app/Presenters/ColumnsPresenter.php | 17 +++++------------ app/Presenters/EditPresenter.php | 4 +--- app/Presenters/Error4xxPresenter.php | 1 - app/Presenters/ErrorPresenter.php | 3 +-- app/Presenters/ExportPresenter.php | 4 +--- app/Presenters/FiltersPresenter.php | 4 +--- app/Presenters/GroupActionsPresenter.php | 9 ++------- app/Presenters/LocalizationPresenter.php | 4 +--- app/Presenters/RowPresenter.php | 14 +++----------- app/Presenters/TreeViewPresenter.php | 16 ++-------------- app/UI/TEmptyLayoutView.php | 20 +++++--------------- 15 files changed, 31 insertions(+), 87 deletions(-) diff --git a/Makefile b/Makefile index 4ec9279..a6ab698 100644 --- a/Makefile +++ b/Makefile @@ -24,13 +24,17 @@ clean: qa: cs phpstan cs: - vendor/bin/codesniffer app +ifdef GITHUB_ACTION + vendor/bin/phpcs --standard=ruleset.xml --extensions=php,phpt --tab-width=4 --ignore=tests/tmp -q --report=checkstyle app tests | cs2pr +else + vendor/bin/phpcs --standard=ruleset.xml --extensions=php,phpt --tab-width=4 --ignore=tests/tmp --colors -nsp app tests +endif csf: - vendor/bin/codefixer app + vendor/bin/phpcbf --standard=ruleset.xml --extensions=php,phpt --tab-width=4 --ignore=tests/tmp --colors -nsp app tests phpstan: - vendor/bin/phpstan analyse -c phpstan.neon --memory-limit=512M app + vendor/bin/phpstan analyse -c phpstan.neon --memory-limit=512M tests: echo "OK" diff --git a/app/Presenters/AbstractPresenter.php b/app/Presenters/AbstractPresenter.php index ed71e3a..3bb793c 100644 --- a/app/Presenters/AbstractPresenter.php +++ b/app/Presenters/AbstractPresenter.php @@ -15,10 +15,7 @@ abstract class AbstractPresenter extends Presenter abstract public function createComponentGrid(): DataGrid; - /** - * @param mixed $id - */ - public function changeStatus($id, string $newStatus): void + public function changeStatus(mixed $id, string $newStatus): void { $id = (int) $id; diff --git a/app/Presenters/ActionsPresenter.php b/app/Presenters/ActionsPresenter.php index 27ccbbf..46f4f9f 100644 --- a/app/Presenters/ActionsPresenter.php +++ b/app/Presenters/ActionsPresenter.php @@ -69,21 +69,18 @@ public function createComponentGrid(): DataGrid return $grid; } - public function handleSort(): void { $this->flashMessage('Sorted!'); $this->redrawControl('flashes'); } - public function handleBlah(): void { $this->flashMessage('Blah'); $this->redrawControl('flashes'); } - public function handleDelete(): void { $this->flashMessage('Deleted!', 'info'); diff --git a/app/Presenters/BasicPresenter.php b/app/Presenters/BasicPresenter.php index da91f3b..e6c8cac 100644 --- a/app/Presenters/BasicPresenter.php +++ b/app/Presenters/BasicPresenter.php @@ -34,9 +34,7 @@ public function createComponentGrid(): DataGrid ->setFormat('j. n. Y'); $grid->addColumnNumber('age', 'Age') - ->setRenderer(function (Row $row): int { - return $row['birth_date']->diff(new DateTime())->y; - }); + ->setRenderer(fn (Row $row): int => $row['birth_date']->diff(new DateTime())->y); return $grid; } diff --git a/app/Presenters/ColumnsPresenter.php b/app/Presenters/ColumnsPresenter.php index e1ac41e..e17879e 100644 --- a/app/Presenters/ColumnsPresenter.php +++ b/app/Presenters/ColumnsPresenter.php @@ -61,9 +61,7 @@ public function createComponentGrid(): DataGrid ->setSortable(); $grid->addColumnNumber('age', 'Age') - ->setRenderer(function (Row $row): int { - return $row['birth_date']->diff(new DateTime())->y; - }); + ->setRenderer(fn (Row $row): int => $row['birth_date']->diff(new DateTime())->y); $grid->setColumnsHideable(); @@ -80,9 +78,7 @@ public function createComponentGrid(): DataGrid $grid->addColumnCallback('email', function (ColumnLink $column, Row $row): void { if ($row['id'] === 3) { - $column->setRenderer(function (): string { - return ''; - }); + $column->setRenderer(fn (): string => ''); } }); @@ -92,19 +88,16 @@ public function createComponentGrid(): DataGrid new class implements IMultipleAggregationFunction { - /** @var int */ - private $idsSum = 0; + private int $idsSum = 0; - /** @var float */ - private $avgAge = 0.0; + private float $avgAge = 0.0; public function getFilterDataType(): string { return IAggregationFunction::DATA_TYPE_PAGINATED; } - /** @param mixed $dataSource */ - public function processDataSource($dataSource): void + public function processDataSource(mixed $dataSource): void { if (!$dataSource instanceof Fluent) { throw new UnexpectedValueException(); diff --git a/app/Presenters/EditPresenter.php b/app/Presenters/EditPresenter.php index 0388be1..70fd60b 100644 --- a/app/Presenters/EditPresenter.php +++ b/app/Presenters/EditPresenter.php @@ -34,9 +34,7 @@ public function createComponentGrid(): DataGrid $grid->addColumnLink('link', 'Link', 'this#demo', 'name', ['id', 'surname' => 'name']) ->setEditableValueCallback( - function (Row $row) { - return $row['name']; - } + fn (Row $row) => $row['name'] ) ->setEditableCallback(function ($id, $value): string { $this->flashMessage(sprintf('Id: %s, new value: %s', $id, $value)); diff --git a/app/Presenters/Error4xxPresenter.php b/app/Presenters/Error4xxPresenter.php index 40e97d3..eada95b 100644 --- a/app/Presenters/Error4xxPresenter.php +++ b/app/Presenters/Error4xxPresenter.php @@ -23,7 +23,6 @@ public function startup(): void } } - public function renderDefault(BadRequestException $exception): void { // load template 403.latte or 404.latte or ... 4xx.latte diff --git a/app/Presenters/ErrorPresenter.php b/app/Presenters/ErrorPresenter.php index 729a4dc..3748044 100644 --- a/app/Presenters/ErrorPresenter.php +++ b/app/Presenters/ErrorPresenter.php @@ -19,8 +19,7 @@ final class ErrorPresenter implements IPresenter use SmartObject; - /** @var ILogger */ - private $logger; + private ILogger $logger; public function __construct(ILogger $logger) { diff --git a/app/Presenters/ExportPresenter.php b/app/Presenters/ExportPresenter.php index 6c1220f..7118646 100644 --- a/app/Presenters/ExportPresenter.php +++ b/app/Presenters/ExportPresenter.php @@ -43,9 +43,7 @@ public function createComponentGrid(): DataGrid $columnName = new ColumnText($grid, 'name', 'name', 'Name'); $columnEven = (new ColumnText($grid, 'even', 'even', 'Even ID (yes/no)')) ->setRenderer( - function ($item) { - return $item['id'] % 2 === 0 ? 'No' : 'Yes'; - } + fn ($item) => $item['id'] % 2 === 0 ? 'No' : 'Yes' ); $grid->addExportCsv('Csv export', 'examples-all.csv') diff --git a/app/Presenters/FiltersPresenter.php b/app/Presenters/FiltersPresenter.php index 7f8224f..3477a63 100644 --- a/app/Presenters/FiltersPresenter.php +++ b/app/Presenters/FiltersPresenter.php @@ -48,9 +48,7 @@ public function createComponentGrid(): DataGrid ->setFilterDateRange(); $grid->addColumnNumber('age', 'Age') - ->setRenderer(function (Row $row): int { - return $row['birth_date']->diff(new DateTime())->y; - }) + ->setRenderer(fn (Row $row): int => $row['birth_date']->diff(new DateTime())->y) ->setFilterRange() ->setCondition(function (Fluent $fluent, ArrayHash $values): void { if ((bool) $values['from']) { diff --git a/app/Presenters/GroupActionsPresenter.php b/app/Presenters/GroupActionsPresenter.php index b817fdf..4e10f8d 100644 --- a/app/Presenters/GroupActionsPresenter.php +++ b/app/Presenters/GroupActionsPresenter.php @@ -40,8 +40,8 @@ public function createComponentGrid(): DataGrid )->onSelect[] = [$this, 'groupChangeStatus']; $grid->addGroupAction('Send', [ - 'john' => 'John', - 'joe' => 'Joe', + 'john' => 'John', + 'joe' => 'Joe', 'frank' => 'Frank', ])->onSelect[] = [$this, 'groupSend']; @@ -54,7 +54,6 @@ public function createComponentGrid(): DataGrid return $grid; } - /** * @param mixed[] $ids */ @@ -85,7 +84,6 @@ public function groupChangeStatus(array $ids, string $newStatus): void } } - /** * @param mixed[] $ids */ @@ -104,7 +102,6 @@ public function groupAddNote(array $ids, string $value): void } } - /** * @param mixed[] $ids */ @@ -123,7 +120,6 @@ public function groupSend(array $ids, string $key): void } } - /** * @param mixed[] $ids */ @@ -142,7 +138,6 @@ public function groupDelete(array $ids): void } } - /** * @param mixed[] $ids */ diff --git a/app/Presenters/LocalizationPresenter.php b/app/Presenters/LocalizationPresenter.php index 261f484..9591b20 100644 --- a/app/Presenters/LocalizationPresenter.php +++ b/app/Presenters/LocalizationPresenter.php @@ -35,9 +35,7 @@ public function createComponentGrid(): DataGrid ->setFormat('j. n. Y'); $grid->addColumnNumber('age', 'Age') - ->setRenderer(function (Row $row): int { - return $row['birth_date']->diff(new DateTime())->y; - }); + ->setRenderer(fn (Row $row): int => $row['birth_date']->diff(new DateTime())->y); $translator = new SimpleTranslator([ 'ublaboo_datagrid.no_item_found_reset' => 'Žádné položky nenalezeny. Filtr můžete vynulovat', diff --git a/app/Presenters/RowPresenter.php b/app/Presenters/RowPresenter.php index f67e5c0..3905790 100644 --- a/app/Presenters/RowPresenter.php +++ b/app/Presenters/RowPresenter.php @@ -46,29 +46,21 @@ public function createComponentGrid(): DataGrid $grid->addGroupAction('Delete')->onSelect[] = [$this, 'groupDelete']; - $grid->allowRowsGroupAction(function ($item): bool { - return $item->id % 2 === 0; - }); + $grid->allowRowsGroupAction(fn ($item): bool => $item->id % 2 === 0); - $grid->allowRowsAction('delete', function ($item): bool { - return $item->id % 3 === 0; - }); + $grid->allowRowsAction('delete', fn ($item): bool => $item->id % 3 === 0); - $grid->allowRowsAction('detail', function ($item): bool { - return $item->id % 4 === 0; - }); + $grid->allowRowsAction('detail', fn ($item): bool => $item->id % 4 === 0); return $grid; } - public function handleDelete(): void { $this->flashMessage('Deleted!', 'info'); $this->redrawControl('flashes'); } - /** * @param mixed[] $ids */ diff --git a/app/Presenters/TreeViewPresenter.php b/app/Presenters/TreeViewPresenter.php index 3e276cf..0770249 100644 --- a/app/Presenters/TreeViewPresenter.php +++ b/app/Presenters/TreeViewPresenter.php @@ -68,12 +68,10 @@ public function createComponentGrid(): DataGrid return $grid; } - /** - * @param mixed $parentCategoryId * @return Fluent */ - public function getChildren($parentCategoryId): Fluent + public function getChildren(mixed $parentCategoryId): Fluent { $join = $this->dibiConnection->select('COUNT(id) AS count, parent_category_id') ->from('categories') @@ -87,15 +85,7 @@ public function getChildren($parentCategoryId): Fluent ->where('c.parent_category_id = ?', (int) $parentCategoryId); } - - - /** - * @param mixed $itemId - * @param mixed $prevId - * @param mixed $nextId - * @param mixed $parentId - */ - public function handleSort($itemId, $prevId, $nextId, $parentId): void + public function handleSort(mixed $itemId, mixed $prevId, mixed $nextId, mixed $parentId): void { $this->flashMessage( sprintf( @@ -115,7 +105,6 @@ public function handleSort($itemId, $prevId, $nextId, $parentId): void } } - public function handleEdit(): void { $this->flashMessage('Edited!', 'success'); @@ -127,7 +116,6 @@ public function handleEdit(): void } } - public function handleDelete(): void { $this->flashMessage('Deleted!', 'info'); diff --git a/app/UI/TEmptyLayoutView.php b/app/UI/TEmptyLayoutView.php index b6e5421..1d367d1 100644 --- a/app/UI/TEmptyLayoutView.php +++ b/app/UI/TEmptyLayoutView.php @@ -1,12 +1,8 @@ -getRequest(); - if ($request->getParameter('inFrame') == true) { + if ($request->getParameter('inFrame') === true) { $this->setLayout(__DIR__ . '/../templates/@layout.inFrame.latte'); } } + } From 4632af36f1ecee64e91ea9b08b0211cc193ea830 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Tue, 24 Jan 2023 11:55:26 +0100 Subject: [PATCH 11/34] Config: common -> services --- app/Bootstrap.php | 2 +- config/{common.neon => services.neon} | 0 2 files changed, 1 insertion(+), 1 deletion(-) rename config/{common.neon => services.neon} (100%) diff --git a/app/Bootstrap.php b/app/Bootstrap.php index 2494eea..40665ee 100644 --- a/app/Bootstrap.php +++ b/app/Bootstrap.php @@ -17,7 +17,7 @@ public static function boot(): Configurator $configurator->setTimeZone('Europe/Prague'); $configurator->setTempDirectory(__DIR__ . '/../temp'); - $configurator->addConfig(__DIR__ . '/../config/common.neon'); + $configurator->addConfig(__DIR__ . '/../config/services.neon'); if (file_exists(__DIR__ . '/../config/local.neon')) { $configurator->addConfig(__DIR__ . '/../config/local.neon'); diff --git a/config/common.neon b/config/services.neon similarity index 100% rename from config/common.neon rename to config/services.neon From 4fa3599cfe8054c548d6d18b3244a60853c7a9dd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Tue, 24 Jan 2023 11:55:34 +0100 Subject: [PATCH 12/34] Config: example of local.neon --- .gitignore | 3 +++ config/.gitignore | 1 - config/local.neon.example | 3 +++ 3 files changed, 6 insertions(+), 1 deletion(-) delete mode 100644 config/.gitignore create mode 100644 config/local.neon.example diff --git a/.gitignore b/.gitignore index db7c641..5577fb4 100644 --- a/.gitignore +++ b/.gitignore @@ -3,3 +3,6 @@ # Node /node_modules + +# Nette +/config/local.neon diff --git a/config/.gitignore b/config/.gitignore deleted file mode 100644 index ffe2f35..0000000 --- a/config/.gitignore +++ /dev/null @@ -1 +0,0 @@ -local.neon diff --git a/config/local.neon.example b/config/local.neon.example new file mode 100644 index 0000000..12b6ebf --- /dev/null +++ b/config/local.neon.example @@ -0,0 +1,3 @@ +parameters: + +services: From cae0420a3cb808313632bd2b45ee28c0a7e497eb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Tue, 24 Jan 2023 12:21:32 +0100 Subject: [PATCH 13/34] Tests: init --- Makefile | 8 ++++++-- composer.json | 1 + tests/.coveralls.yml | 4 ++++ tests/.gitignore | 3 +++ tests/Cases/Build/EntrypointTest.php | 18 ++++++++++++++++++ tests/bootstrap.php | 7 +++++++ 6 files changed, 39 insertions(+), 2 deletions(-) create mode 100644 tests/.coveralls.yml create mode 100644 tests/.gitignore create mode 100644 tests/Cases/Build/EntrypointTest.php create mode 100644 tests/bootstrap.php diff --git a/Makefile b/Makefile index a6ab698..5e6d2cf 100644 --- a/Makefile +++ b/Makefile @@ -37,10 +37,14 @@ phpstan: vendor/bin/phpstan analyse -c phpstan.neon --memory-limit=512M tests: - echo "OK" + vendor/bin/tester -s -p php --colors 1 -C tests/Cases coverage: - echo "OK" +ifdef GITHUB_ACTION + vendor/bin/tester -s -p phpdbg --colors 1 -C --coverage coverage.xml --coverage-src app tests/Cases +else + vendor/bin/tester -s -p phpdbg --colors 1 -C --coverage coverage.html --coverage-src app tests/Cases +endif dev: NETTE_DEBUG=1 NETTE_ENV=dev php -S 0.0.0.0:8000 -t www diff --git a/composer.json b/composer.json index 6d3b0b6..aca1d92 100644 --- a/composer.json +++ b/composer.json @@ -34,6 +34,7 @@ }, "require-dev": { "contributte/qa": "^0.4.0", + "contributte/tester": "^0.1.0", "phpstan/phpstan": "^1.9.14", "phpstan/phpstan-dibi": "^1.0.1", "phpstan/phpstan-nette": "^1.2.1", diff --git a/tests/.coveralls.yml b/tests/.coveralls.yml new file mode 100644 index 0000000..8450382 --- /dev/null +++ b/tests/.coveralls.yml @@ -0,0 +1,4 @@ +# for php-coveralls +service_name: github-actions +coverage_clover: coverage.xml +json_path: coverage.json diff --git a/tests/.gitignore b/tests/.gitignore new file mode 100644 index 0000000..e3886ad --- /dev/null +++ b/tests/.gitignore @@ -0,0 +1,3 @@ +output +/test.log +/tmp diff --git a/tests/Cases/Build/EntrypointTest.php b/tests/Cases/Build/EntrypointTest.php new file mode 100644 index 0000000..74e66ab --- /dev/null +++ b/tests/Cases/Build/EntrypointTest.php @@ -0,0 +1,18 @@ +createContainer(); + $container->getByType(Application::class); + + Assert::type(Container::class, $container); +}); diff --git a/tests/bootstrap.php b/tests/bootstrap.php new file mode 100644 index 0000000..b09de76 --- /dev/null +++ b/tests/bootstrap.php @@ -0,0 +1,7 @@ + Date: Tue, 24 Jan 2023 11:57:40 +0100 Subject: [PATCH 14/34] CI: refactor workflows --- .github/workflows/codesniffer.yml | 17 ++++ .github/workflows/coverage.yml | 20 +++++ .github/workflows/main.yaml | 133 ------------------------------ .github/workflows/phpstan.yml | 17 ++++ .github/workflows/tests.yml | 32 +++++++ 5 files changed, 86 insertions(+), 133 deletions(-) create mode 100644 .github/workflows/codesniffer.yml create mode 100644 .github/workflows/coverage.yml delete mode 100644 .github/workflows/main.yaml create mode 100644 .github/workflows/phpstan.yml create mode 100644 .github/workflows/tests.yml diff --git a/.github/workflows/codesniffer.yml b/.github/workflows/codesniffer.yml new file mode 100644 index 0000000..60ccf92 --- /dev/null +++ b/.github/workflows/codesniffer.yml @@ -0,0 +1,17 @@ +name: "Codesniffer" + +on: + pull_request: + + push: + branches: ["*"] + + schedule: + - cron: "0 8 * * 1" + +jobs: + codesniffer: + name: "Codesniffer" + uses: contributte/.github/.github/workflows/codesniffer.yml@v1 + with: + php: "8.2" diff --git a/.github/workflows/coverage.yml b/.github/workflows/coverage.yml new file mode 100644 index 0000000..c5e7125 --- /dev/null +++ b/.github/workflows/coverage.yml @@ -0,0 +1,20 @@ +name: "Coverage" + +on: + pull_request: + + push: + branches: ["*"] + + schedule: + - cron: "0 8 * * 1" + +jobs: + test80: + name: "Nette Tester" + uses: contributte/.github/.github/workflows/nette-tester-mysql.yml@v1 + with: + php: "8.2" + database: tests + coverage: true + make: coverage diff --git a/.github/workflows/main.yaml b/.github/workflows/main.yaml deleted file mode 100644 index 8e4ef16..0000000 --- a/.github/workflows/main.yaml +++ /dev/null @@ -1,133 +0,0 @@ -name: "build" - -on: - pull_request: - paths-ignore: - - ".docs/**" - push: - branches: - - "*" - schedule: - - cron: "0 8 * * 1" # At 08:00 on Monday - -env: - extensions: "json" - cacheVersion: "1" - composerVersion: "v2" - composerInstall: "composer install" - -jobs: - qa: - name: "Quality Assurance" - runs-on: "${{ matrix.operating-system }}" - - strategy: - matrix: - php-versions: [ "8.0" ] - operating-system: [ "ubuntu-latest" ] - fail-fast: false - - steps: - - name: "Checkout" - uses: "actions/checkout@v2" - - - name: "Setup PHP cache environment" - id: "extcache" - uses: "shivammathur/cache-extensions@v1" - with: - php-version: "${{ matrix.php-versions }}" - extensions: "${{ env.extensions }}" - key: "${{ env.cacheVersion }}" - - - name: "Cache PHP extensions" - uses: "actions/cache@v2" - with: - path: "${{ steps.extcache.outputs.dir }}" - key: "${{ steps.extcache.outputs.key }}" - restore-keys: "${{ steps.extcache.outputs.key }}" - - - name: "Install PHP" - uses: "shivammathur/setup-php@v2" - with: - php-version: "${{ matrix.php-versions }}" - extensions: "${{ env.extensions }}" - tools: "composer:${{ env.composerVersion }} " - - - name: "Setup problem matchers for PHP" - run: 'echo "::add-matcher::${{ runner.tool_cache }}/php.json"' - - - name: "Get Composer cache directory" - id: "composercache" - run: 'echo "::set-output name=dir::$(composer config cache-files-dir)"' - - - name: "Cache PHP dependencies" - uses: "actions/cache@v2" - with: - path: "${{ steps.composercache.outputs.dir }}" - key: "${{ runner.os }}-composer-${{ hashFiles('**/composer.json') }}" - restore-keys: "${{ runner.os }}-composer-" - - - name: "Validate Composer" - run: "composer validate" - - - name: "Install dependencies" - run: "${{ env.composerInstall }}" - - - name: "Coding Standard" - run: "make cs" - - static-analysis: - name: "Static analysis" - runs-on: "${{ matrix.operating-system }}" - - strategy: - matrix: - php-versions: [ "8.0" ] - operating-system: [ "ubuntu-latest" ] - fail-fast: false - - steps: - - name: "Checkout" - uses: "actions/checkout@v2" - - - name: "Setup PHP cache environment" - id: "extcache" - uses: "shivammathur/cache-extensions@v1" - with: - php-version: "${{ matrix.php-versions }}" - extensions: "${{ env.extensions }}" - key: "${{ env.cacheVersion }}" - - - name: "Cache PHP extensions" - uses: "actions/cache@v2" - with: - path: "${{ steps.extcache.outputs.dir }}" - key: "${{ steps.extcache.outputs.key }}" - restore-keys: "${{ steps.extcache.outputs.key }}" - - - name: "Install PHP" - uses: "shivammathur/setup-php@v2" - with: - php-version: "${{ matrix.php-versions }}" - extensions: "${{ env.extensions }}" - tools: "composer:${{ env.composerVersion }} " - - - name: "Setup problem matchers for PHP" - run: 'echo "::add-matcher::${{ runner.tool_cache }}/php.json"' - - - name: "Get Composer cache directory" - id: "composercache" - run: 'echo "::set-output name=dir::$(composer config cache-files-dir)"' - - - name: "Cache PHP dependencies" - uses: "actions/cache@v2" - with: - path: "${{ steps.composercache.outputs.dir }}" - key: "${{ runner.os }}-composer-${{ hashFiles('**/composer.json') }}" - restore-keys: "${{ runner.os }}-composer-" - - - name: "Install dependencies" - run: "${{ env.composerInstall }}" - - - name: "PHPStan" - run: "make phpstan" diff --git a/.github/workflows/phpstan.yml b/.github/workflows/phpstan.yml new file mode 100644 index 0000000..131be8e --- /dev/null +++ b/.github/workflows/phpstan.yml @@ -0,0 +1,17 @@ +name: "Phpstan" + +on: + pull_request: + + push: + branches: ["*"] + + schedule: + - cron: "0 8 * * 1" + +jobs: + phpstan: + name: "Phpstan" + uses: contributte/.github/.github/workflows/phpstan.yml@v1 + with: + php: "8.2" diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml new file mode 100644 index 0000000..4cf5475 --- /dev/null +++ b/.github/workflows/tests.yml @@ -0,0 +1,32 @@ +name: "Nette Tester" + +on: + pull_request: + + push: + branches: ["*"] + + schedule: + - cron: "0 8 * * 1" + +jobs: + test82: + name: "Nette Tester" + uses: contributte/.github/.github/workflows/nette-tester-mysql.yml@v1 + with: + php: "8.2" + database: tests + + test81: + name: "Nette Tester" + uses: contributte/.github/.github/workflows/nette-tester-mysql.yml@v1 + with: + php: "8.1" + database: tests + + test80: + name: "Nette Tester" + uses: contributte/.github/.github/workflows/nette-tester-mysql.yml@v1 + with: + php: "8.0" + database: tests From d86ac2e9a920ef5659522298038b258594268633 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Tue, 24 Jan 2023 12:18:18 +0100 Subject: [PATCH 15/34] App: upgrade to PHP 8.1, phpstan level 9 --- .github/workflows/tests.yml | 7 ------ app/Model/Utils/DateTime.php | 20 +++++++++++++++++ app/Model/Utils/Types.php | 28 ++++++++++++++++++++++++ app/Presenters/AbstractPresenter.php | 4 +--- app/Presenters/BasicPresenter.php | 4 ++-- app/Presenters/ColumnsPresenter.php | 13 ++++++----- app/Presenters/EditPresenter.php | 3 ++- app/Presenters/FiltersPresenter.php | 4 ++-- app/Presenters/LocalizationPresenter.php | 4 ++-- app/Presenters/TreeViewPresenter.php | 6 ++--- app/UI/TEmptyLayoutView.php | 2 +- composer.json | 2 +- phpstan.neon | 10 ++++++++- 13 files changed, 78 insertions(+), 29 deletions(-) create mode 100644 app/Model/Utils/DateTime.php create mode 100644 app/Model/Utils/Types.php diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index 4cf5475..a817aa1 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -23,10 +23,3 @@ jobs: with: php: "8.1" database: tests - - test80: - name: "Nette Tester" - uses: contributte/.github/.github/workflows/nette-tester-mysql.yml@v1 - with: - php: "8.0" - database: tests diff --git a/app/Model/Utils/DateTime.php b/app/Model/Utils/DateTime.php new file mode 100644 index 0000000..7ffa6fb --- /dev/null +++ b/app/Model/Utils/DateTime.php @@ -0,0 +1,20 @@ + $newStatus]; diff --git a/app/Presenters/BasicPresenter.php b/app/Presenters/BasicPresenter.php index e6c8cac..805d0dc 100644 --- a/app/Presenters/BasicPresenter.php +++ b/app/Presenters/BasicPresenter.php @@ -2,8 +2,8 @@ namespace App\Presenters; +use App\Model\Utils\DateTime; use App\UI\TEmptyLayoutView; -use DateTime; use Dibi\Row; use Ublaboo\DataGrid\DataGrid; @@ -34,7 +34,7 @@ public function createComponentGrid(): DataGrid ->setFormat('j. n. Y'); $grid->addColumnNumber('age', 'Age') - ->setRenderer(fn (Row $row): int => $row['birth_date']->diff(new DateTime())->y); + ->setRenderer(fn (Row $row): ?int => DateTime::fromSafe($row->asDateTime('birth_date'))?->diff(new DateTime())->y); return $grid; } diff --git a/app/Presenters/ColumnsPresenter.php b/app/Presenters/ColumnsPresenter.php index e17879e..9303c50 100644 --- a/app/Presenters/ColumnsPresenter.php +++ b/app/Presenters/ColumnsPresenter.php @@ -2,8 +2,9 @@ namespace App\Presenters; +use App\Model\Utils\DateTime; +use App\Model\Utils\Types; use App\UI\TEmptyLayoutView; -use DateTime; use Dibi\Fluent; use Dibi\Row; use Ublaboo\DataGrid\AggregationFunction\IAggregationFunction; @@ -61,7 +62,7 @@ public function createComponentGrid(): DataGrid ->setSortable(); $grid->addColumnNumber('age', 'Age') - ->setRenderer(fn (Row $row): int => $row['birth_date']->diff(new DateTime())->y); + ->setRenderer(fn (Row $row): ?int => DateTime::fromSafe($row->asDateTime('birth_date'))?->diff(new DateTime())->y); $grid->setColumnsHideable(); @@ -103,15 +104,15 @@ public function processDataSource(mixed $dataSource): void throw new UnexpectedValueException(); } - $this->idsSum = (int) $dataSource->getConnection() + $this->idsSum = Types::forceInt($dataSource->getConnection() ->select('SUM([id])') ->from($dataSource, '_') - ->fetchSingle(); + ->fetchSingle()); - $this->avgAge = round((float) $dataSource->getConnection() + $this->avgAge = round(Types::forceNumber($dataSource->getConnection() ->select('AVG(YEAR([birth_date]))') ->from($dataSource, '_') - ->fetchSingle()); + ->fetchSingle())); } public function renderResult(string $key): string diff --git a/app/Presenters/EditPresenter.php b/app/Presenters/EditPresenter.php index 70fd60b..7299941 100644 --- a/app/Presenters/EditPresenter.php +++ b/app/Presenters/EditPresenter.php @@ -2,6 +2,7 @@ namespace App\Presenters; +use App\Model\Utils\DateTime; use App\UI\TEmptyLayoutView; use Dibi\Row; use Nette\Forms\Container; @@ -67,7 +68,7 @@ public function createComponentGrid(): DataGrid $container->setDefaults([ 'id' => $row['id'], 'name' => $row['name'], - 'birth_date' => $row['birth_date']->format('j. n. Y'), + 'birth_date' => DateTime::fromSafe($row->asDateTime('birth_date'))?->format('j. n. Y'), 'link' => $row['name'], 'status' => $row['status'], ]); diff --git a/app/Presenters/FiltersPresenter.php b/app/Presenters/FiltersPresenter.php index 3477a63..816e4b4 100644 --- a/app/Presenters/FiltersPresenter.php +++ b/app/Presenters/FiltersPresenter.php @@ -2,8 +2,8 @@ namespace App\Presenters; +use App\Model\Utils\DateTime; use App\UI\TEmptyLayoutView; -use DateTime; use Dibi\Fluent; use Dibi\Row; use Nette\Utils\ArrayHash; @@ -48,7 +48,7 @@ public function createComponentGrid(): DataGrid ->setFilterDateRange(); $grid->addColumnNumber('age', 'Age') - ->setRenderer(fn (Row $row): int => $row['birth_date']->diff(new DateTime())->y) + ->setRenderer(fn (Row $row): ?int => DateTime::fromSafe($row->asDateTime('birth_date'))?->diff(new DateTime())->y) ->setFilterRange() ->setCondition(function (Fluent $fluent, ArrayHash $values): void { if ((bool) $values['from']) { diff --git a/app/Presenters/LocalizationPresenter.php b/app/Presenters/LocalizationPresenter.php index 9591b20..174d71a 100644 --- a/app/Presenters/LocalizationPresenter.php +++ b/app/Presenters/LocalizationPresenter.php @@ -2,8 +2,8 @@ namespace App\Presenters; +use App\Model\Utils\DateTime; use App\UI\TEmptyLayoutView; -use DateTime; use Dibi\Row; use Ublaboo\DataGrid\DataGrid; use Ublaboo\DataGrid\Localization\SimpleTranslator; @@ -35,7 +35,7 @@ public function createComponentGrid(): DataGrid ->setFormat('j. n. Y'); $grid->addColumnNumber('age', 'Age') - ->setRenderer(fn (Row $row): int => $row['birth_date']->diff(new DateTime())->y); + ->setRenderer(fn (Row $row): ?int => DateTime::fromSafe($row->asDateTime('birth_date'))?->diff(new DateTime())->y); $translator = new SimpleTranslator([ 'ublaboo_datagrid.no_item_found_reset' => 'Žádné položky nenalezeny. Filtr můžete vynulovat', diff --git a/app/Presenters/TreeViewPresenter.php b/app/Presenters/TreeViewPresenter.php index 0770249..9a582a7 100644 --- a/app/Presenters/TreeViewPresenter.php +++ b/app/Presenters/TreeViewPresenter.php @@ -71,7 +71,7 @@ public function createComponentGrid(): DataGrid /** * @return Fluent */ - public function getChildren(mixed $parentCategoryId): Fluent + public function getChildren(int $parentCategoryId): Fluent { $join = $this->dibiConnection->select('COUNT(id) AS count, parent_category_id') ->from('categories') @@ -82,10 +82,10 @@ public function getChildren(mixed $parentCategoryId): Fluent ->from('categories', 'c') ->leftJoin($join, 'c_b') ->on('c_b.parent_category_id = c.id') - ->where('c.parent_category_id = ?', (int) $parentCategoryId); + ->where('c.parent_category_id = ?', $parentCategoryId); } - public function handleSort(mixed $itemId, mixed $prevId, mixed $nextId, mixed $parentId): void + public function handleSort(int $itemId, int $prevId, int $nextId, int $parentId): void { $this->flashMessage( sprintf( diff --git a/app/UI/TEmptyLayoutView.php b/app/UI/TEmptyLayoutView.php index 1d367d1..f239aef 100644 --- a/app/UI/TEmptyLayoutView.php +++ b/app/UI/TEmptyLayoutView.php @@ -17,7 +17,7 @@ public function renderDefault(): void { $request = $this->getRequest(); - if ($request->getParameter('inFrame') === true) { + if ($request !== null && $request->getParameter('inFrame') === true) { $this->setLayout(__DIR__ . '/../templates/@layout.inFrame.latte'); } } diff --git a/composer.json b/composer.json index aca1d92..1b92d4d 100644 --- a/composer.json +++ b/composer.json @@ -13,7 +13,7 @@ "license": "MIT", "type": "project", "require": { - "php": ">= 8.0", + "php": ">= 8.1", "nette/application": "^3.1.0", "nette/bootstrap": "^3.2.0", diff --git a/phpstan.neon b/phpstan.neon index 7c5cbd9..5a9c7c2 100644 --- a/phpstan.neon +++ b/phpstan.neon @@ -6,7 +6,15 @@ includes: - vendor/phpstan/phpstan-dibi/extension.neon parameters: - level: 8 + level: 9 + phpVersion: 80100 + + tmpDir: %currentWorkingDirectory%/temp/phpstan paths: - app + + fileExtensions: + - php + + ignoreErrors: From a9fa47e2263cc2b4a3163b81719e477b0722164e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:26:12 +0100 Subject: [PATCH 16/34] Add .env files --- .env.dist | 11 +++++++++++ .env.example | 2 ++ 2 files changed, 13 insertions(+) create mode 100644 .env.dist create mode 100644 .env.example diff --git a/.env.dist b/.env.dist new file mode 100644 index 0000000..20a638d --- /dev/null +++ b/.env.dist @@ -0,0 +1,11 @@ +DB_DATABASE=contributte +DB_USER=contributte +DB_PASSWORD=contributte +DB_ROOT_PASSWORD=contributte + +XDEBUG_MODE=debug +XDEBUG_HOST=host.docker.internal +XDEBUG_CONFIG= + +NETTE_DEBUG=0 +NETTE_ENV=production diff --git a/.env.example b/.env.example new file mode 100644 index 0000000..286eaa0 --- /dev/null +++ b/.env.example @@ -0,0 +1,2 @@ +NETTE_DEBUG=1 +NETTE_ENV=development From ee14ca501b1f35091ccf3ae7e13e6d9675d4a409 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:26:17 +0100 Subject: [PATCH 17/34] Update gitignore --- .gitignore | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/.gitignore b/.gitignore index 5577fb4..d37ab58 100644 --- a/.gitignore +++ b/.gitignore @@ -1,8 +1,20 @@ +# IDE +.idea + +# Docker +/.docker + # Composer /vendor +# Nette +/config/local.neon + +# Assets +/www/dist + # Node /node_modules -# Nette -/config/local.neon +# Envs +.env From ff429f24cb70460db4dd076fbcdd0c143d8a7923 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:26:24 +0100 Subject: [PATCH 18/34] Composer: based on nella --- composer.json | 16 +- composer.lock | 1881 ++++++++++++++++++++++++++++--------------------- 2 files changed, 1074 insertions(+), 823 deletions(-) diff --git a/composer.json b/composer.json index 1b92d4d..0c897cf 100644 --- a/composer.json +++ b/composer.json @@ -1,6 +1,6 @@ { "name": "contributte/datagrid-skeleton", - "description": "Datagrid component project skeleton based on Nette Framework and Contributte libraries by @f3l1x & @paveljanda.", + "description": "Example of contributte/datagrid component. Project skeleton based on Nette Framework and Contributte libraries by @f3l1x & @paveljanda.", "keywords": [ "php", "nette", @@ -15,21 +15,9 @@ "require": { "php": ">= 8.1", - "nette/application": "^3.1.0", - "nette/bootstrap": "^3.2.0", - "nette/caching": "^3.2.0", - "nette/database": "^3.1.0", - "nette/di": "^3.0.15", - "nette/forms": "^3.1.0", - "nette/http": "^3.2.0", - "nette/utils": "^3.2.0", - - "latte/latte": "^3.0.3", - "tracy/tracy": "^2.9.5", - + "contributte/nella": "^0.1", "ublaboo/datagrid": "dev-next", - "nextras/orm": "^4.0.6", "dibi/dibi": "^4.2.7" }, "require-dev": { diff --git a/composer.lock b/composer.lock index 97f5089..ff20027 100644 --- a/composer.lock +++ b/composer.lock @@ -4,36 +4,37 @@ "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", "This file is @generated automatically" ], - "content-hash": "59c41fc2243812dd0d1dd1a9cf919f5b", + "content-hash": "c3cd2f19a97d67000400c328a59e7527", "packages": [ { "name": "contributte/application", - "version": "v0.5.2", + "version": "v0.5.1", "source": { "type": "git", "url": "https://github.com/contributte/application.git", - "reference": "f5f8637bd54eacd1cc45792f23bb8831873ddb35" + "reference": "2579ab2bc3b7c95ae32a2e664ac9a8cc038777f9" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/contributte/application/zipball/f5f8637bd54eacd1cc45792f23bb8831873ddb35", - "reference": "f5f8637bd54eacd1cc45792f23bb8831873ddb35", + "url": "https://api.github.com/repos/contributte/application/zipball/2579ab2bc3b7c95ae32a2e664ac9a8cc038777f9", + "reference": "2579ab2bc3b7c95ae32a2e664ac9a8cc038777f9", "shasum": "" }, "require": { - "nette/application": "^3.0.0 || ^4.0", + "nette/application": "^3.0.0", "php": ">=7.2" }, "require-dev": { - "nette/http": "~2.4.8 || ^3.0.0", + "nette/http": "~2.4.8 || ~3.0.0", "ninjify/nunjuck": "^0.3.0", - "ninjify/qa": "^0.13.0", - "phpstan/phpstan": "^1.0", - "phpstan/phpstan-deprecation-rules": "^1.0", - "phpstan/phpstan-nette": "^1.0", - "phpstan/phpstan-strict-rules": "^1.0", + "ninjify/qa": "^0.9.0", + "phpstan/extension-installer": "^1.0", + "phpstan/phpstan-deprecation-rules": "^0.11.0", + "phpstan/phpstan-nette": "^0.11.1", + "phpstan/phpstan-shim": "^0.11.2", + "phpstan/phpstan-strict-rules": "^0.11.0", "psr/http-message": "~1.0.1", - "tracy/tracy": "~2.9.1" + "tracy/tracy": "~2.6.1" }, "type": "library", "extra": { @@ -67,7 +68,385 @@ ], "support": { "issues": "https://github.com/contributte/application/issues", - "source": "https://github.com/contributte/application/tree/v0.5.2" + "source": "https://github.com/contributte/application/tree/v0.5.1" + }, + "funding": [ + { + "url": "https://contributte.org/partners.html", + "type": "custom" + }, + { + "url": "https://github.com/f3l1x", + "type": "github" + } + ], + "time": "2021-03-10T21:48:30+00:00" + }, + { + "name": "contributte/bootstrap", + "version": "v0.5.0", + "source": { + "type": "git", + "url": "https://github.com/contributte/bootstrap.git", + "reference": "55c2358ef001b922896f9a8faaa0282e67a64d09" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/contributte/bootstrap/zipball/55c2358ef001b922896f9a8faaa0282e67a64d09", + "reference": "55c2358ef001b922896f9a8faaa0282e67a64d09", + "shasum": "" + }, + "require": { + "nette/bootstrap": "^3.0.2", + "nette/utils": "^3.1.5", + "php": ">=7.2" + }, + "require-dev": { + "ninjify/nunjuck": "^0.4", + "ninjify/qa": "^0.12", + "phpstan/phpstan": "^0.12", + "phpstan/phpstan-deprecation-rules": "^0.12", + "phpstan/phpstan-nette": "^0.12", + "phpstan/phpstan-strict-rules": "^0.12" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "0.6-dev" + } + }, + "autoload": { + "psr-4": { + "Contributte\\Bootstrap\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Milan Felix Šulc", + "homepage": "https://f3l1x.io" + } + ], + "description": "Extra contrib to nette/boostrap", + "homepage": "https://github.com/contributte/bootstrap", + "keywords": [ + "application", + "bootstrap", + "docker", + "nette" + ], + "support": { + "issues": "https://github.com/contributte/bootstrap/issues", + "source": "https://github.com/contributte/bootstrap/tree/v0.5.0" + }, + "time": "2020-12-13T19:07:20+00:00" + }, + { + "name": "contributte/di", + "version": "v0.5.5", + "source": { + "type": "git", + "url": "https://github.com/contributte/di.git", + "reference": "2857d07b15c8d0136038f4daa6930c42491a6f6a" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/contributte/di/zipball/2857d07b15c8d0136038f4daa6930c42491a6f6a", + "reference": "2857d07b15c8d0136038f4daa6930c42491a6f6a", + "shasum": "" + }, + "require": { + "nette/di": "^3.1.0", + "nette/utils": "^3.2.8 || ^4.0", + "php": ">=7.2" + }, + "conflict": { + "nette/schema": "<1.1.0" + }, + "require-dev": { + "nette/bootstrap": "^3.1.4", + "nette/robot-loader": "^3.4.2 || ^4.0", + "ninjify/nunjuck": "^0.4", + "ninjify/qa": "^0.13", + "phpstan/phpstan": "^1.9.11", + "phpstan/phpstan-deprecation-rules": "^1.1.1", + "phpstan/phpstan-nette": "^1.2.0", + "phpstan/phpstan-strict-rules": "^1.4.5" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "0.6.x-dev" + } + }, + "autoload": { + "psr-4": { + "Contributte\\DI\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Milan Felix Šulc", + "homepage": "https://f3l1x.io" + } + ], + "description": "Extra contrib to nette/di", + "homepage": "https://github.com/contributte/di", + "keywords": [ + "dependency", + "inject", + "nette" + ], + "support": { + "issues": "https://github.com/contributte/di/issues", + "source": "https://github.com/contributte/di/tree/v0.5.5" + }, + "funding": [ + { + "url": "https://contributte.org/partners.html", + "type": "custom" + }, + { + "url": "https://github.com/f3l1x", + "type": "github" + } + ], + "time": "2023-02-21T08:24:32+00:00" + }, + { + "name": "contributte/forms", + "version": "v0.5.1", + "source": { + "type": "git", + "url": "https://github.com/contributte/forms.git", + "reference": "c7ac26b456ff2958ea207c43be6515ad1154dcea" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/contributte/forms/zipball/c7ac26b456ff2958ea207c43be6515ad1154dcea", + "reference": "c7ac26b456ff2958ea207c43be6515ad1154dcea", + "shasum": "" + }, + "require": { + "nette/forms": "^3.0.0", + "php": ">=7.2" + }, + "conflict": { + "nette/di": "<3.0.0" + }, + "require-dev": { + "nette/application": "^3.0.0", + "nette/di": "^3.1.0", + "ninjify/nunjuck": "^0.4", + "ninjify/qa": "^0.12", + "phpstan/phpstan": "^1.0", + "phpstan/phpstan-deprecation-rules": "^1.0", + "phpstan/phpstan-nette": "^1.0", + "phpstan/phpstan-strict-rules": "^1.1" + }, + "suggest": { + "nette/di": "to use FormFactoryExtension[CompilerExtension]" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "0.6.x-dev" + } + }, + "autoload": { + "psr-4": { + "Contributte\\Forms\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Milan Felix Šulc", + "homepage": "https://f3l1x.io" + } + ], + "description": "Extra contrib to nette/forms", + "homepage": "https://github.com/contributte/forms", + "keywords": [ + "Forms", + "checkbox", + "inputs", + "nette", + "renderers", + "rules", + "validation" + ], + "support": { + "issues": "https://github.com/contributte/forms/issues", + "source": "https://github.com/contributte/forms/tree/v0.5.1" + }, + "funding": [ + { + "url": "https://contributte.org/partners.html", + "type": "custom" + }, + { + "url": "https://github.com/f3l1x", + "type": "github" + } + ], + "time": "2022-11-13T17:22:04+00:00" + }, + { + "name": "contributte/latte", + "version": "dev-master", + "source": { + "type": "git", + "url": "https://github.com/contributte/latte.git", + "reference": "6e11db54b4cf0f4579b58b69150ef74b67a1f414" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/contributte/latte/zipball/6e11db54b4cf0f4579b58b69150ef74b67a1f414", + "reference": "6e11db54b4cf0f4579b58b69150ef74b67a1f414", + "shasum": "" + }, + "require": { + "latte/latte": "^2.5.1 || ^3.0", + "php": ">=7.2" + }, + "conflict": { + "nette/di": "<3.0.0" + }, + "require-dev": { + "nette/application": "^3.0", + "nette/di": "~3.0.0", + "ninjify/nunjuck": "^0.4", + "ninjify/qa": "^0.12", + "phpstan/phpstan": "^1.0", + "phpstan/phpstan-deprecation-rules": "^1.0", + "phpstan/phpstan-nette": "^1.0", + "phpstan/phpstan-strict-rules": "^1.0" + }, + "suggest": { + "nette/di": "to use VersionExtension[CompilerExtension]" + }, + "default-branch": true, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "0.6.x-dev" + } + }, + "autoload": { + "psr-4": { + "Contributte\\Latte\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Milan Felix Šulc", + "homepage": "https://f3l1x.io" + } + ], + "description": "Extra contrib to nette/latte", + "homepage": "https://github.com/contributte/latte", + "keywords": [ + "extra", + "latte", + "nette" + ], + "support": { + "issues": "https://github.com/contributte/latte/issues", + "source": "https://github.com/contributte/latte/tree/master" + }, + "funding": [ + { + "url": "https://contributte.org/partners.html", + "type": "custom" + }, + { + "url": "https://github.com/f3l1x", + "type": "github" + } + ], + "time": "2023-02-13T16:14:37+00:00" + }, + { + "name": "contributte/nella", + "version": "dev-master", + "source": { + "type": "git", + "url": "https://github.com/contributte/nella.git", + "reference": "bdb893fd6be8049d2b728f993ddba8362475e2dc" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/contributte/nella/zipball/bdb893fd6be8049d2b728f993ddba8362475e2dc", + "reference": "bdb893fd6be8049d2b728f993ddba8362475e2dc", + "shasum": "" + }, + "require": { + "contributte/application": "^0.5.0", + "contributte/bootstrap": "^0.5.0", + "contributte/di": "^0.5.1", + "contributte/forms": "^0.5.0", + "contributte/latte": "^0.6.0", + "contributte/tracy": "^0.5.1", + "contributte/utils": "^0.5.0", + "php": ">=8.0" + }, + "require-dev": { + "contributte/qa": "^0.2.0", + "contributte/tester": "^0.1.0", + "mockery/mockery": "^1.5.0", + "phpstan/phpstan": "^1.2.0", + "phpstan/phpstan-deprecation-rules": "^1.0.0", + "phpstan/phpstan-nette": "^1.0.0", + "phpstan/phpstan-strict-rules": "^1.1.0" + }, + "default-branch": true, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "0.1.x-dev" + } + }, + "autoload": { + "psr-4": { + "Contributte\\Nella\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Milan Felix Šulc", + "homepage": "https://f3l1x.io" + } + ], + "description": "Opinionated pre-configured kernel based on Nette (@nette). Suitable for all kind apps.", + "homepage": "https://github.com/contributte/nella", + "keywords": [ + "kernel", + "nella", + "nette", + "stack" + ], + "support": { + "issues": "https://github.com/contributte/nella/issues", + "source": "https://github.com/contributte/nella/tree/master" }, "funding": [ { @@ -79,39 +458,190 @@ "type": "github" } ], - "time": "2023-09-27T20:32:37+00:00" + "time": "2023-03-07T19:43:10+00:00" + }, + { + "name": "contributte/tracy", + "version": "v0.5.1", + "source": { + "type": "git", + "url": "https://github.com/contributte/tracy.git", + "reference": "eefc7596f348145c23ce81653b89a68b79653e67" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/contributte/tracy/zipball/eefc7596f348145c23ce81653b89a68b79653e67", + "reference": "eefc7596f348145c23ce81653b89a68b79653e67", + "shasum": "" + }, + "require": { + "php": ">=7.2", + "tracy/tracy": "^2.7.0" + }, + "conflict": { + "nette/di": "<3.0.0" + }, + "require-dev": { + "nette/application": "~3.0.0", + "nette/di": "~3.0.0", + "nette/http": "~3.0.1", + "ninjify/nunjuck": "^0.4", + "ninjify/qa": "^0.12", + "phpstan/phpstan": "^0.12", + "phpstan/phpstan-deprecation-rules": "^0.12", + "phpstan/phpstan-nette": "^0.12", + "phpstan/phpstan-strict-rules": "^0.12" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "0.6.x-dev" + } + }, + "autoload": { + "psr-4": { + "Contributte\\Tracy\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Milan Felix Šulc", + "homepage": "https://f3l1x.io" + }, + { + "name": "Marek Bartoš", + "homepage": "https://marek-bartos.cz" + } + ], + "description": "Tuned Tracy Bars/Panels/BlueScreens for easy-developing", + "homepage": "https://github.com/contributte/tracy", + "keywords": [ + "bluescreen", + "develop", + "navigation", + "nette", + "profile", + "tracy" + ], + "support": { + "issues": "https://github.com/contributte/tracy/issues", + "source": "https://github.com/contributte/tracy/tree/v0.5.1" + }, + "time": "2020-12-19T17:38:47+00:00" + }, + { + "name": "contributte/utils", + "version": "v0.5.2", + "source": { + "type": "git", + "url": "https://github.com/contributte/utils.git", + "reference": "e2d9c380dbb179cf15a66555924ab2792b2c1769" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/contributte/utils/zipball/e2d9c380dbb179cf15a66555924ab2792b2c1769", + "reference": "e2d9c380dbb179cf15a66555924ab2792b2c1769", + "shasum": "" + }, + "require": { + "nette/utils": "^3.0.1", + "php": ">=7.2" + }, + "conflict": { + "nette/di": "<3.0.0" + }, + "require-dev": { + "nette/di": "^3.1.0", + "ninjify/nunjuck": "^0.4.0", + "ninjify/qa": "^0.12.0", + "phpstan/phpstan": "^1.9.0", + "phpstan/phpstan-deprecation-rules": "^1.1.0", + "phpstan/phpstan-nette": "^1.2.0", + "phpstan/phpstan-strict-rules": "^1.4.0" + }, + "suggest": { + "nette/di": "to use DateTimeExtension[CompilerExtension]" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "0.6.x-dev" + } + }, + "autoload": { + "psr-4": { + "Contributte\\Utils\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Milan Felix Šulc", + "homepage": "https://f3l1x.io" + } + ], + "description": "Extra contrib to nette/utils", + "homepage": "https://github.com/contributte/utils", + "keywords": [ + "datetime", + "filesystem", + "nette", + "strings", + "utils" + ], + "support": { + "issues": "https://github.com/contributte/utils/issues", + "source": "https://github.com/contributte/utils/tree/v0.5.2" + }, + "funding": [ + { + "url": "https://contributte.org/partners.html", + "type": "custom" + }, + { + "url": "https://github.com/f3l1x", + "type": "github" + } + ], + "time": "2022-12-26T13:10:34+00:00" }, { "name": "dibi/dibi", - "version": "v5.0.1", + "version": "v4.2.7", "source": { "type": "git", "url": "https://github.com/dg/dibi.git", - "reference": "86a71dde28fd1c1b55e4c66a6f7ebfd4efb13e1d" + "reference": "7fa05f381b23fdc59af98caeb03b1ae8ed1e03ed" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/dg/dibi/zipball/86a71dde28fd1c1b55e4c66a6f7ebfd4efb13e1d", - "reference": "86a71dde28fd1c1b55e4c66a6f7ebfd4efb13e1d", + "url": "https://api.github.com/repos/dg/dibi/zipball/7fa05f381b23fdc59af98caeb03b1ae8ed1e03ed", + "reference": "7fa05f381b23fdc59af98caeb03b1ae8ed1e03ed", "shasum": "" }, "require": { - "php": "8.0 - 8.3" + "php": ">=7.2" }, "replace": { "dg/dibi": "*" }, "require-dev": { - "jetbrains/phpstorm-attributes": "^1.0", - "nette/di": "^3.1", - "nette/tester": "^2.5", - "phpstan/phpstan": "^1.0", - "tracy/tracy": "^2.9" + "nette/di": "^3.0", + "nette/tester": "~2.0", + "phpstan/phpstan": "^0.12", + "tracy/tracy": "~2.2" }, "type": "library", "extra": { "branch-alias": { - "dev-master": "5.0-dev" + "dev-master": "4.2-dev" } }, "autoload": { @@ -148,28 +678,28 @@ ], "support": { "issues": "https://github.com/dg/dibi/issues", - "source": "https://github.com/dg/dibi/tree/v5.0.1" + "source": "https://github.com/dg/dibi/tree/v4.2.7" }, - "time": "2023-11-25T13:08:47+00:00" + "time": "2022-11-18T03:40:51+00:00" }, { "name": "latte/latte", - "version": "v3.0.15", + "version": "v3.0.5", "source": { "type": "git", "url": "https://github.com/nette/latte.git", - "reference": "b4807f2f6ef774adb946da1b174e1e85171a9101" + "reference": "1ccb0add4ddc5e8b5db3b82a145fa9ff2d9d6f8f" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/latte/zipball/b4807f2f6ef774adb946da1b174e1e85171a9101", - "reference": "b4807f2f6ef774adb946da1b174e1e85171a9101", + "url": "https://api.github.com/repos/nette/latte/zipball/1ccb0add4ddc5e8b5db3b82a145fa9ff2d9d6f8f", + "reference": "1ccb0add4ddc5e8b5db3b82a145fa9ff2d9d6f8f", "shasum": "" }, "require": { "ext-json": "*", "ext-tokenizer": "*", - "php": "8.0 - 8.3" + "php": ">=8.0 <8.3" }, "conflict": { "nette/application": "<3.1.7", @@ -233,33 +763,33 @@ ], "support": { "issues": "https://github.com/nette/latte/issues", - "source": "https://github.com/nette/latte/tree/v3.0.15" + "source": "https://github.com/nette/latte/tree/v3.0.5" }, - "time": "2024-04-30T05:57:23+00:00" + "time": "2023-01-16T23:22:36+00:00" }, { "name": "nette/application", - "version": "v3.1.14", + "version": "v3.1.10", "source": { "type": "git", "url": "https://github.com/nette/application.git", - "reference": "0729ede7e66fad642046a3eb670d368845272573" + "reference": "9c31b24407623437c1e1345cc2bd4e210b290135" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/application/zipball/0729ede7e66fad642046a3eb670d368845272573", - "reference": "0729ede7e66fad642046a3eb670d368845272573", + "url": "https://api.github.com/repos/nette/application/zipball/9c31b24407623437c1e1345cc2bd4e210b290135", + "reference": "9c31b24407623437c1e1345cc2bd4e210b290135", "shasum": "" }, "require": { "nette/component-model": "^3.0", "nette/http": "^3.0.2", - "nette/routing": "^3.0.5", + "nette/routing": "^3.0.2", "nette/utils": "^3.2.1 || ~4.0.0", "php": ">=7.2" }, "conflict": { - "latte/latte": "<2.7.1 || >=3.0.0 <3.0.8 || >=3.1", + "latte/latte": "<2.7.1 || >=3.0.0 <3.0.5 || >=3.1", "nette/caching": "<3.1", "nette/di": "<3.0.7", "nette/forms": "<3.0", @@ -325,41 +855,41 @@ ], "support": { "issues": "https://github.com/nette/application/issues", - "source": "https://github.com/nette/application/tree/v3.1.14" + "source": "https://github.com/nette/application/tree/v3.1.10" }, - "time": "2023-10-09T02:45:43+00:00" + "time": "2023-01-17T13:52:03+00:00" }, { "name": "nette/bootstrap", - "version": "v3.2.3", + "version": "v3.2.0", "source": { "type": "git", "url": "https://github.com/nette/bootstrap.git", - "reference": "5f8b9420b0b5441b55f0745dd0e8afa1653e5e6c" + "reference": "7fde23cc8a8cf97d545baf0ad7f8cd47c73feb17" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/bootstrap/zipball/5f8b9420b0b5441b55f0745dd0e8afa1653e5e6c", - "reference": "5f8b9420b0b5441b55f0745dd0e8afa1653e5e6c", + "url": "https://api.github.com/repos/nette/bootstrap/zipball/7fde23cc8a8cf97d545baf0ad7f8cd47c73feb17", + "reference": "7fde23cc8a8cf97d545baf0ad7f8cd47c73feb17", "shasum": "" }, "require": { "nette/di": "^3.1", "nette/utils": "^3.2.1 || ^4.0", - "php": "8.0 - 8.3" + "php": ">=8.0 <8.3" }, "conflict": { "tracy/tracy": "<2.6" }, "require-dev": { - "latte/latte": "^2.8 || ^3.0", + "latte/latte": "^2.8", "nette/application": "^3.1", "nette/caching": "^3.0", "nette/database": "^3.0", "nette/forms": "^3.0", "nette/http": "^3.0", - "nette/mail": "^3.0 || ^4.0", - "nette/robot-loader": "^3.0 || ^4.0", + "nette/mail": "^3.0", + "nette/robot-loader": "^3.0", "nette/safe-stream": "^2.2", "nette/security": "^3.0", "nette/tester": "^2.4", @@ -368,76 +898,7 @@ }, "suggest": { "nette/robot-loader": "to use Configurator::createRobotLoader()", - "tracy/tracy": "to use Configurator::enableTracy()" - }, - "type": "library", - "extra": { - "branch-alias": { - "dev-master": "3.2-dev" - } - }, - "autoload": { - "classmap": [ - "src/" - ] - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "BSD-3-Clause", - "GPL-2.0-only", - "GPL-3.0-only" - ], - "authors": [ - { - "name": "David Grudl", - "homepage": "https://davidgrudl.com" - }, - { - "name": "Nette Community", - "homepage": "https://nette.org/contributors" - } - ], - "description": "🅱 Nette Bootstrap: the simple way to configure and bootstrap your Nette application.", - "homepage": "https://nette.org", - "keywords": [ - "bootstrapping", - "configurator", - "nette" - ], - "support": { - "issues": "https://github.com/nette/bootstrap/issues", - "source": "https://github.com/nette/bootstrap/tree/v3.2.3" - }, - "time": "2024-04-19T00:07:13+00:00" - }, - { - "name": "nette/caching", - "version": "v3.2.3", - "source": { - "type": "git", - "url": "https://github.com/nette/caching.git", - "reference": "6821d74c1db82c493c02c47f6485022d79b63176" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/nette/caching/zipball/6821d74c1db82c493c02c47f6485022d79b63176", - "reference": "6821d74c1db82c493c02c47f6485022d79b63176", - "shasum": "" - }, - "require": { - "nette/finder": "^2.4 || ^3.0", - "nette/utils": "^3.2 || ~4.0.0", - "php": "8.0 - 8.3" - }, - "require-dev": { - "latte/latte": "^2.11 || ^3.0", - "nette/di": "^3.1 || ^4.0", - "nette/tester": "^2.4", - "phpstan/phpstan": "^1.0", - "tracy/tracy": "^2.9" - }, - "suggest": { - "ext-pdo_sqlite": "to use SQLiteStorage or SQLiteJournal" + "tracy/tracy": "to use Configurator::enableTracy()" }, "type": "library", "extra": { @@ -466,20 +927,18 @@ "homepage": "https://nette.org/contributors" } ], - "description": "⏱ Nette Caching: library with easy-to-use API and many cache backends.", + "description": "🅱 Nette Bootstrap: the simple way to configure and bootstrap your Nette application.", "homepage": "https://nette.org", "keywords": [ - "cache", - "journal", - "memcached", - "nette", - "sqlite" + "bootstrapping", + "configurator", + "nette" ], "support": { - "issues": "https://github.com/nette/caching/issues", - "source": "https://github.com/nette/caching/tree/v3.2.3" + "issues": "https://github.com/nette/bootstrap/issues", + "source": "https://github.com/nette/bootstrap/tree/v3.2.0" }, - "time": "2023-09-26T11:12:20+00:00" + "time": "2023-01-13T04:09:35+00:00" }, { "name": "nette/component-model", @@ -543,96 +1002,18 @@ }, "time": "2023-01-09T20:16:05+00:00" }, - { - "name": "nette/database", - "version": "v3.1.9", - "source": { - "type": "git", - "url": "https://github.com/nette/database.git", - "reference": "4a21417d545e226a8fe189b95111d23a454bd2b3" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/nette/database/zipball/4a21417d545e226a8fe189b95111d23a454bd2b3", - "reference": "4a21417d545e226a8fe189b95111d23a454bd2b3", - "shasum": "" - }, - "require": { - "ext-pdo": "*", - "nette/caching": "^3.0", - "nette/utils": "^3.2.1 || ~4.0.0", - "php": "7.2 - 8.3" - }, - "conflict": { - "nette/di": "<3.0-stable" - }, - "require-dev": { - "jetbrains/phpstorm-attributes": "^1.0", - "mockery/mockery": "^1.3.4", - "nette/di": "^v3.0", - "nette/tester": "^2.4", - "phpstan/phpstan-nette": "^0.12", - "tracy/tracy": "^2.4" - }, - "type": "library", - "extra": { - "branch-alias": { - "dev-master": "3.1-dev" - } - }, - "autoload": { - "classmap": [ - "src/" - ] - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "BSD-3-Clause", - "GPL-2.0-only", - "GPL-3.0-only" - ], - "authors": [ - { - "name": "David Grudl", - "homepage": "https://davidgrudl.com" - }, - { - "name": "Nette Community", - "homepage": "https://nette.org/contributors" - } - ], - "description": "💾 Nette Database: layer with a familiar PDO-like API but much more powerful. Building queries, advanced joins, drivers for MySQL, PostgreSQL, SQLite, MS SQL Server and Oracle.", - "homepage": "https://nette.org", - "keywords": [ - "database", - "mssql", - "mysql", - "nette", - "notorm", - "oracle", - "pdo", - "postgresql", - "queries", - "sqlite" - ], - "support": { - "issues": "https://github.com/nette/database/issues", - "source": "https://github.com/nette/database/tree/v3.1.9" - }, - "time": "2023-11-05T19:41:36+00:00" - }, { "name": "nette/di", - "version": "v3.1.10", + "version": "v3.1.1", "source": { "type": "git", "url": "https://github.com/nette/di.git", - "reference": "2645ec3eaa17fa2ab87c5eb4eaacb1fe6dd28284" + "reference": "4799ee684453bf5e70df1e87bec80bfbfc0e7d13" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/di/zipball/2645ec3eaa17fa2ab87c5eb4eaacb1fe6dd28284", - "reference": "2645ec3eaa17fa2ab87c5eb4eaacb1fe6dd28284", + "url": "https://api.github.com/repos/nette/di/zipball/4799ee684453bf5e70df1e87bec80bfbfc0e7d13", + "reference": "4799ee684453bf5e70df1e87bec80bfbfc0e7d13", "shasum": "" }, "require": { @@ -640,9 +1021,9 @@ "nette/neon": "^3.3 || ^4.0", "nette/php-generator": "^3.5.4 || ^4.0", "nette/robot-loader": "^3.2 || ~4.0.0", - "nette/schema": "^1.2.5", + "nette/schema": "^1.2", "nette/utils": "^3.2.5 || ~4.0.0", - "php": "7.2 - 8.3" + "php": ">=7.2 <8.3" }, "require-dev": { "nette/tester": "^2.4", @@ -689,9 +1070,9 @@ ], "support": { "issues": "https://github.com/nette/di/issues", - "source": "https://github.com/nette/di/tree/v3.1.10" + "source": "https://github.com/nette/di/tree/v3.1.1" }, - "time": "2024-02-06T01:19:44+00:00" + "time": "2023-01-16T03:38:02+00:00" }, { "name": "nette/finder", @@ -762,38 +1143,35 @@ }, { "name": "nette/forms", - "version": "v3.1.15", + "version": "v3.1.10", "source": { "type": "git", "url": "https://github.com/nette/forms.git", - "reference": "f373bcd5ea7a33672fa96035d4bf3110ab66ee44" + "reference": "12b4c12e9d65a4c97e10a37cee88fdd14db780b7" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/forms/zipball/f373bcd5ea7a33672fa96035d4bf3110ab66ee44", - "reference": "f373bcd5ea7a33672fa96035d4bf3110ab66ee44", + "url": "https://api.github.com/repos/nette/forms/zipball/12b4c12e9d65a4c97e10a37cee88fdd14db780b7", + "reference": "12b4c12e9d65a4c97e10a37cee88fdd14db780b7", "shasum": "" }, "require": { "nette/component-model": "^3.0", "nette/http": "^3.1", "nette/utils": "^3.2.5 || ~4.0.0", - "php": "7.2 - 8.3" + "php": ">=7.2 <8.3" }, "conflict": { - "latte/latte": ">=3.0.0 <3.0.12 || >=3.1" + "latte/latte": ">=3.1" }, "require-dev": { - "latte/latte": "^2.10.2 || ^3.0.12", + "latte/latte": "^2.10.2 || ^3.0.3", "nette/application": "^3.0", "nette/di": "^3.0", "nette/tester": "^2.4", "phpstan/phpstan-nette": "^1", "tracy/tracy": "^2.9" }, - "suggest": { - "ext-intl": "to use date/time controls" - }, "type": "library", "extra": { "branch-alias": { @@ -833,27 +1211,27 @@ ], "support": { "issues": "https://github.com/nette/forms/issues", - "source": "https://github.com/nette/forms/tree/v3.1.15" + "source": "https://github.com/nette/forms/tree/v3.1.10" }, - "time": "2024-01-21T22:22:16+00:00" + "time": "2023-01-19T14:37:56+00:00" }, { "name": "nette/http", - "version": "v3.2.4", + "version": "v3.2.1", "source": { "type": "git", "url": "https://github.com/nette/http.git", - "reference": "d7cc833ee186d5139cde5aab43b39ee7aedd6f22" + "reference": "0e16cd4f911665679b96bf569318a0dc7f087eda" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/http/zipball/d7cc833ee186d5139cde5aab43b39ee7aedd6f22", - "reference": "d7cc833ee186d5139cde5aab43b39ee7aedd6f22", + "url": "https://api.github.com/repos/nette/http/zipball/0e16cd4f911665679b96bf569318a0dc7f087eda", + "reference": "0e16cd4f911665679b96bf569318a0dc7f087eda", "shasum": "" }, "require": { "nette/utils": "^3.2.1 || ~4.0.0", - "php": "7.2 - 8.3" + "php": ">=7.2 <8.3" }, "conflict": { "nette/di": "<3.0.3", @@ -867,10 +1245,7 @@ "tracy/tracy": "^2.8" }, "suggest": { - "ext-fileinfo": "to detect MIME type of uploaded files by Nette\\Http\\FileUpload", - "ext-gd": "to use image function in Nette\\Http\\FileUpload", - "ext-intl": "to support punycode by Nette\\Http\\Url", - "ext-session": "to use Nette\\Http\\Session" + "ext-fileinfo": "to detect type of uploaded files" }, "type": "library", "extra": { @@ -914,101 +1289,27 @@ ], "support": { "issues": "https://github.com/nette/http/issues", - "source": "https://github.com/nette/http/tree/v3.2.4" - }, - "time": "2024-01-30T18:13:43+00:00" - }, - { - "name": "nette/mail", - "version": "v3.1.11", - "source": { - "type": "git", - "url": "https://github.com/nette/mail.git", - "reference": "804d70278458452863a2d6be4c1d5bf5f91b3950" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/nette/mail/zipball/804d70278458452863a2d6be4c1d5bf5f91b3950", - "reference": "804d70278458452863a2d6be4c1d5bf5f91b3950", - "shasum": "" - }, - "require": { - "ext-iconv": "*", - "nette/utils": "^3.1 || ~4.0.0", - "php": "7.1 - 8.3" - }, - "conflict": { - "nette/di": "<3.0-stable" - }, - "require-dev": { - "nette/di": "^3.0.0", - "nette/tester": "^2.0", - "phpstan/phpstan-nette": "^0.12", - "tracy/tracy": "^2.4" - }, - "suggest": { - "ext-fileinfo": "to detect type of attached files", - "ext-openssl": "to use Nette\\Mail\\DkimSigner" - }, - "type": "library", - "extra": { - "branch-alias": { - "dev-master": "3.1-dev" - } - }, - "autoload": { - "classmap": [ - "src/" - ] - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "BSD-3-Clause", - "GPL-2.0-only", - "GPL-3.0-only" - ], - "authors": [ - { - "name": "David Grudl", - "homepage": "https://davidgrudl.com" - }, - { - "name": "Nette Community", - "homepage": "https://nette.org/contributors" - } - ], - "description": "📧 Nette Mail: handy email creation and transfer library for PHP with both text and MIME-compliant support.", - "homepage": "https://nette.org", - "keywords": [ - "mail", - "mailer", - "mime", - "nette", - "smtp" - ], - "support": { - "issues": "https://github.com/nette/mail/issues", - "source": "https://github.com/nette/mail/tree/v3.1.11" + "source": "https://github.com/nette/http/tree/v3.2.1" }, - "time": "2023-11-02T23:18:58+00:00" + "time": "2022-12-05T00:03:40+00:00" }, { "name": "nette/neon", - "version": "v3.4.1", + "version": "v3.4.0", "source": { "type": "git", "url": "https://github.com/nette/neon.git", - "reference": "457bfbf0560f600b30d9df4233af382a478bb44d" + "reference": "372d945c156ee7f35c953339fb164538339e6283" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/neon/zipball/457bfbf0560f600b30d9df4233af382a478bb44d", - "reference": "457bfbf0560f600b30d9df4233af382a478bb44d", + "url": "https://api.github.com/repos/nette/neon/zipball/372d945c156ee7f35c953339fb164538339e6283", + "reference": "372d945c156ee7f35c953339fb164538339e6283", "shasum": "" }, "require": { "ext-json": "*", - "php": "8.0 - 8.3" + "php": ">=8.0 <8.3" }, "require-dev": { "nette/tester": "^2.4", @@ -1056,32 +1357,31 @@ ], "support": { "issues": "https://github.com/nette/neon/issues", - "source": "https://github.com/nette/neon/tree/v3.4.1" + "source": "https://github.com/nette/neon/tree/v3.4.0" }, - "time": "2023-09-27T08:59:11+00:00" + "time": "2023-01-13T03:08:29+00:00" }, { "name": "nette/php-generator", - "version": "v4.1.4", + "version": "v4.0.5", "source": { "type": "git", "url": "https://github.com/nette/php-generator.git", - "reference": "b135071d8da108445e4df2fc6a75522b23c0237d" + "reference": "a8d6abeae5d8c7202cd69600e086a7a72877fc86" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/php-generator/zipball/b135071d8da108445e4df2fc6a75522b23c0237d", - "reference": "b135071d8da108445e4df2fc6a75522b23c0237d", + "url": "https://api.github.com/repos/nette/php-generator/zipball/a8d6abeae5d8c7202cd69600e086a7a72877fc86", + "reference": "a8d6abeae5d8c7202cd69600e086a7a72877fc86", "shasum": "" }, "require": { - "nette/utils": "^3.2.9 || ^4.0", - "php": "8.0 - 8.3" + "nette/utils": "^3.2.7 || ^4.0", + "php": ">=8.0 <8.3" }, "require-dev": { - "jetbrains/phpstorm-attributes": "dev-master", "nette/tester": "^2.4", - "nikic/php-parser": "^4.18 || ^5.0", + "nikic/php-parser": "^4.15", "phpstan/phpstan": "^1.0", "tracy/tracy": "^2.8" }, @@ -1091,7 +1391,7 @@ "type": "library", "extra": { "branch-alias": { - "dev-master": "4.1-dev" + "dev-master": "4.0-dev" } }, "autoload": { @@ -1115,7 +1415,7 @@ "homepage": "https://nette.org/contributors" } ], - "description": "🐘 Nette PHP Generator: generates neat PHP code for you. Supports new PHP 8.3 features.", + "description": "🐘 Nette PHP Generator: generates neat PHP code for you. Supports new PHP 8.2 features.", "homepage": "https://nette.org", "keywords": [ "code", @@ -1125,9 +1425,9 @@ ], "support": { "issues": "https://github.com/nette/php-generator/issues", - "source": "https://github.com/nette/php-generator/tree/v4.1.4" + "source": "https://github.com/nette/php-generator/tree/v4.0.5" }, - "time": "2024-03-07T23:06:26+00:00" + "time": "2022-11-02T20:37:46+00:00" }, { "name": "nette/robot-loader", @@ -1198,16 +1498,16 @@ }, { "name": "nette/routing", - "version": "v3.0.5", + "version": "v3.0.4", "source": { "type": "git", "url": "https://github.com/nette/routing.git", - "reference": "ff709ff9ed38a14c4fe3472534526593a8461ff5" + "reference": "eaefe6375303799366f3e43977daaf33f5f89b95" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/routing/zipball/ff709ff9ed38a14c4fe3472534526593a8461ff5", - "reference": "ff709ff9ed38a14c4fe3472534526593a8461ff5", + "url": "https://api.github.com/repos/nette/routing/zipball/eaefe6375303799366f3e43977daaf33f5f89b95", + "reference": "eaefe6375303799366f3e43977daaf33f5f89b95", "shasum": "" }, "require": { @@ -1254,27 +1554,27 @@ ], "support": { "issues": "https://github.com/nette/routing/issues", - "source": "https://github.com/nette/routing/tree/v3.0.5" + "source": "https://github.com/nette/routing/tree/v3.0.4" }, - "time": "2023-10-08T21:37:46+00:00" + "time": "2023-01-18T04:58:41+00:00" }, { "name": "nette/schema", - "version": "v1.2.5", + "version": "v1.2.3", "source": { "type": "git", "url": "https://github.com/nette/schema.git", - "reference": "0462f0166e823aad657c9224d0f849ecac1ba10a" + "reference": "abbdbb70e0245d5f3bf77874cea1dfb0c930d06f" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/schema/zipball/0462f0166e823aad657c9224d0f849ecac1ba10a", - "reference": "0462f0166e823aad657c9224d0f849ecac1ba10a", + "url": "https://api.github.com/repos/nette/schema/zipball/abbdbb70e0245d5f3bf77874cea1dfb0c930d06f", + "reference": "abbdbb70e0245d5f3bf77874cea1dfb0c930d06f", "shasum": "" }, "require": { "nette/utils": "^2.5.7 || ^3.1.5 || ^4.0", - "php": "7.1 - 8.3" + "php": ">=7.1 <8.3" }, "require-dev": { "nette/tester": "^2.3 || ^2.4", @@ -1316,97 +1616,26 @@ ], "support": { "issues": "https://github.com/nette/schema/issues", - "source": "https://github.com/nette/schema/tree/v1.2.5" - }, - "time": "2023-10-05T20:37:59+00:00" - }, - { - "name": "nette/security", - "version": "v3.1.8", - "source": { - "type": "git", - "url": "https://github.com/nette/security.git", - "reference": "9b8e5c76b2e738350498470c35a36a6f0d0e38d6" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/nette/security/zipball/9b8e5c76b2e738350498470c35a36a6f0d0e38d6", - "reference": "9b8e5c76b2e738350498470c35a36a6f0d0e38d6", - "shasum": "" - }, - "require": { - "nette/utils": "^3.2.1 || ~4.0.0", - "php": "7.2 - 8.3" - }, - "conflict": { - "nette/di": "<3.0-stable", - "nette/http": "<3.1.3" - }, - "require-dev": { - "mockery/mockery": "^1.3.6", - "nette/di": "^3.0.1", - "nette/http": "^3.0.0", - "nette/tester": "^2.0", - "phpstan/phpstan-nette": "^1.0", - "tracy/tracy": "^2.4" - }, - "type": "library", - "extra": { - "branch-alias": { - "dev-master": "3.1-dev" - } - }, - "autoload": { - "classmap": [ - "src/" - ] - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "BSD-3-Clause", - "GPL-2.0-only", - "GPL-3.0-only" - ], - "authors": [ - { - "name": "David Grudl", - "homepage": "https://davidgrudl.com" - }, - { - "name": "Nette Community", - "homepage": "https://nette.org/contributors" - } - ], - "description": "🔑 Nette Security: provides authentication, authorization and a role-based access control management via ACL (Access Control List)", - "homepage": "https://nette.org", - "keywords": [ - "Authentication", - "acl", - "authorization", - "nette" - ], - "support": { - "issues": "https://github.com/nette/security/issues", - "source": "https://github.com/nette/security/tree/v3.1.8" + "source": "https://github.com/nette/schema/tree/v1.2.3" }, - "time": "2023-10-18T17:05:31+00:00" + "time": "2022-10-13T01:24:26+00:00" }, { "name": "nette/utils", - "version": "v3.2.10", + "version": "v3.2.9", "source": { "type": "git", "url": "https://github.com/nette/utils.git", - "reference": "a4175c62652f2300c8017fb7e640f9ccb11648d2" + "reference": "c91bac3470c34b2ecd5400f6e6fdf0b64a836a5c" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/utils/zipball/a4175c62652f2300c8017fb7e640f9ccb11648d2", - "reference": "a4175c62652f2300c8017fb7e640f9ccb11648d2", + "url": "https://api.github.com/repos/nette/utils/zipball/c91bac3470c34b2ecd5400f6e6fdf0b64a836a5c", + "reference": "c91bac3470c34b2ecd5400f6e6fdf0b64a836a5c", "shasum": "" }, "require": { - "php": ">=7.2 <8.4" + "php": ">=7.2 <8.3" }, "conflict": { "nette/di": "<3.0.6" @@ -1473,31 +1702,31 @@ ], "support": { "issues": "https://github.com/nette/utils/issues", - "source": "https://github.com/nette/utils/tree/v3.2.10" + "source": "https://github.com/nette/utils/tree/v3.2.9" }, - "time": "2023-07-30T15:38:18+00:00" + "time": "2023-01-18T03:26:20+00:00" }, { "name": "symfony/deprecation-contracts", - "version": "v2.5.2", + "version": "v3.2.1", "source": { "type": "git", "url": "https://github.com/symfony/deprecation-contracts.git", - "reference": "e8b495ea28c1d97b5e0c121748d6f9b53d075c66" + "reference": "e2d1534420bd723d0ef5aec58a22c5fe60ce6f5e" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/e8b495ea28c1d97b5e0c121748d6f9b53d075c66", - "reference": "e8b495ea28c1d97b5e0c121748d6f9b53d075c66", + "url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/e2d1534420bd723d0ef5aec58a22c5fe60ce6f5e", + "reference": "e2d1534420bd723d0ef5aec58a22c5fe60ce6f5e", "shasum": "" }, "require": { - "php": ">=7.1" + "php": ">=8.1" }, "type": "library", "extra": { "branch-alias": { - "dev-main": "2.5-dev" + "dev-main": "3.3-dev" }, "thanks": { "name": "symfony/contracts", @@ -1526,7 +1755,7 @@ "description": "A generic function and convention to trigger deprecation notices", "homepage": "https://symfony.com", "support": { - "source": "https://github.com/symfony/deprecation-contracts/tree/v2.5.2" + "source": "https://github.com/symfony/deprecation-contracts/tree/v3.2.1" }, "funding": [ { @@ -1542,20 +1771,20 @@ "type": "tidelift" } ], - "time": "2022-01-02T09:53:40+00:00" + "time": "2023-03-01T10:25:55+00:00" }, { "name": "symfony/polyfill-ctype", - "version": "v1.29.0", + "version": "v1.27.0", "source": { "type": "git", "url": "https://github.com/symfony/polyfill-ctype.git", - "reference": "ef4d7e442ca910c4764bce785146269b30cb5fc4" + "reference": "5bbc823adecdae860bb64756d639ecfec17b050a" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/ef4d7e442ca910c4764bce785146269b30cb5fc4", - "reference": "ef4d7e442ca910c4764bce785146269b30cb5fc4", + "url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/5bbc823adecdae860bb64756d639ecfec17b050a", + "reference": "5bbc823adecdae860bb64756d639ecfec17b050a", "shasum": "" }, "require": { @@ -1569,6 +1798,9 @@ }, "type": "library", "extra": { + "branch-alias": { + "dev-main": "1.27-dev" + }, "thanks": { "name": "symfony/polyfill", "url": "https://github.com/symfony/polyfill" @@ -1605,7 +1837,7 @@ "portable" ], "support": { - "source": "https://github.com/symfony/polyfill-ctype/tree/v1.29.0" + "source": "https://github.com/symfony/polyfill-ctype/tree/v1.27.0" }, "funding": [ { @@ -1621,20 +1853,20 @@ "type": "tidelift" } ], - "time": "2024-01-29T20:11:03+00:00" + "time": "2022-11-03T14:55:06+00:00" }, { "name": "symfony/polyfill-intl-grapheme", - "version": "v1.29.0", + "version": "v1.27.0", "source": { "type": "git", "url": "https://github.com/symfony/polyfill-intl-grapheme.git", - "reference": "32a9da87d7b3245e09ac426c83d334ae9f06f80f" + "reference": "511a08c03c1960e08a883f4cffcacd219b758354" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/32a9da87d7b3245e09ac426c83d334ae9f06f80f", - "reference": "32a9da87d7b3245e09ac426c83d334ae9f06f80f", + "url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/511a08c03c1960e08a883f4cffcacd219b758354", + "reference": "511a08c03c1960e08a883f4cffcacd219b758354", "shasum": "" }, "require": { @@ -1645,6 +1877,9 @@ }, "type": "library", "extra": { + "branch-alias": { + "dev-main": "1.27-dev" + }, "thanks": { "name": "symfony/polyfill", "url": "https://github.com/symfony/polyfill" @@ -1683,88 +1918,7 @@ "shim" ], "support": { - "source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.29.0" - }, - "funding": [ - { - "url": "https://symfony.com/sponsor", - "type": "custom" - }, - { - "url": "https://github.com/fabpot", - "type": "github" - }, - { - "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", - "type": "tidelift" - } - ], - "time": "2024-01-29T20:11:03+00:00" - }, - { - "name": "symfony/polyfill-intl-normalizer", - "version": "v1.29.0", - "source": { - "type": "git", - "url": "https://github.com/symfony/polyfill-intl-normalizer.git", - "reference": "bc45c394692b948b4d383a08d7753968bed9a83d" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/symfony/polyfill-intl-normalizer/zipball/bc45c394692b948b4d383a08d7753968bed9a83d", - "reference": "bc45c394692b948b4d383a08d7753968bed9a83d", - "shasum": "" - }, - "require": { - "php": ">=7.1" - }, - "suggest": { - "ext-intl": "For best performance" - }, - "type": "library", - "extra": { - "thanks": { - "name": "symfony/polyfill", - "url": "https://github.com/symfony/polyfill" - } - }, - "autoload": { - "files": [ - "bootstrap.php" - ], - "psr-4": { - "Symfony\\Polyfill\\Intl\\Normalizer\\": "" - }, - "classmap": [ - "Resources/stubs" - ] - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "MIT" - ], - "authors": [ - { - "name": "Nicolas Grekas", - "email": "p@tchwork.com" - }, - { - "name": "Symfony Community", - "homepage": "https://symfony.com/contributors" - } - ], - "description": "Symfony polyfill for intl's Normalizer class and related functions", - "homepage": "https://symfony.com", - "keywords": [ - "compatibility", - "intl", - "normalizer", - "polyfill", - "portable", - "shim" - ], - "support": { - "source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.29.0" + "source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.27.0" }, "funding": [ { @@ -1780,33 +1934,33 @@ "type": "tidelift" } ], - "time": "2024-01-29T20:11:03+00:00" + "time": "2022-11-03T14:55:06+00:00" }, { - "name": "symfony/polyfill-mbstring", - "version": "v1.29.0", + "name": "symfony/polyfill-intl-normalizer", + "version": "v1.27.0", "source": { "type": "git", - "url": "https://github.com/symfony/polyfill-mbstring.git", - "reference": "9773676c8a1bb1f8d4340a62efe641cf76eda7ec" + "url": "https://github.com/symfony/polyfill-intl-normalizer.git", + "reference": "19bd1e4fcd5b91116f14d8533c57831ed00571b6" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/9773676c8a1bb1f8d4340a62efe641cf76eda7ec", - "reference": "9773676c8a1bb1f8d4340a62efe641cf76eda7ec", + "url": "https://api.github.com/repos/symfony/polyfill-intl-normalizer/zipball/19bd1e4fcd5b91116f14d8533c57831ed00571b6", + "reference": "19bd1e4fcd5b91116f14d8533c57831ed00571b6", "shasum": "" }, "require": { "php": ">=7.1" }, - "provide": { - "ext-mbstring": "*" - }, "suggest": { - "ext-mbstring": "For best performance" + "ext-intl": "For best performance" }, "type": "library", "extra": { + "branch-alias": { + "dev-main": "1.27-dev" + }, "thanks": { "name": "symfony/polyfill", "url": "https://github.com/symfony/polyfill" @@ -1817,8 +1971,11 @@ "bootstrap.php" ], "psr-4": { - "Symfony\\Polyfill\\Mbstring\\": "" - } + "Symfony\\Polyfill\\Intl\\Normalizer\\": "" + }, + "classmap": [ + "Resources/stubs" + ] }, "notification-url": "https://packagist.org/downloads/", "license": [ @@ -1834,17 +1991,18 @@ "homepage": "https://symfony.com/contributors" } ], - "description": "Symfony polyfill for the Mbstring extension", + "description": "Symfony polyfill for intl's Normalizer class and related functions", "homepage": "https://symfony.com", "keywords": [ "compatibility", - "mbstring", + "intl", + "normalizer", "polyfill", "portable", "shim" ], "support": { - "source": "https://github.com/symfony/polyfill-mbstring/tree/v1.29.0" + "source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.27.0" }, "funding": [ { @@ -1860,27 +2018,36 @@ "type": "tidelift" } ], - "time": "2024-01-29T20:11:03+00:00" + "time": "2022-11-03T14:55:06+00:00" }, { - "name": "symfony/polyfill-php80", - "version": "v1.29.0", + "name": "symfony/polyfill-mbstring", + "version": "v1.27.0", "source": { "type": "git", - "url": "https://github.com/symfony/polyfill-php80.git", - "reference": "87b68208d5c1188808dd7839ee1e6c8ec3b02f1b" + "url": "https://github.com/symfony/polyfill-mbstring.git", + "reference": "8ad114f6b39e2c98a8b0e3bd907732c207c2b534" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/polyfill-php80/zipball/87b68208d5c1188808dd7839ee1e6c8ec3b02f1b", - "reference": "87b68208d5c1188808dd7839ee1e6c8ec3b02f1b", + "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/8ad114f6b39e2c98a8b0e3bd907732c207c2b534", + "reference": "8ad114f6b39e2c98a8b0e3bd907732c207c2b534", "shasum": "" }, "require": { "php": ">=7.1" }, + "provide": { + "ext-mbstring": "*" + }, + "suggest": { + "ext-mbstring": "For best performance" + }, "type": "library", "extra": { + "branch-alias": { + "dev-main": "1.27-dev" + }, "thanks": { "name": "symfony/polyfill", "url": "https://github.com/symfony/polyfill" @@ -1891,21 +2058,14 @@ "bootstrap.php" ], "psr-4": { - "Symfony\\Polyfill\\Php80\\": "" - }, - "classmap": [ - "Resources/stubs" - ] + "Symfony\\Polyfill\\Mbstring\\": "" + } }, "notification-url": "https://packagist.org/downloads/", "license": [ "MIT" ], "authors": [ - { - "name": "Ion Bazan", - "email": "ion.bazan@gmail.com" - }, { "name": "Nicolas Grekas", "email": "p@tchwork.com" @@ -1915,16 +2075,17 @@ "homepage": "https://symfony.com/contributors" } ], - "description": "Symfony polyfill backporting some PHP 8.0+ features to lower PHP versions", + "description": "Symfony polyfill for the Mbstring extension", "homepage": "https://symfony.com", "keywords": [ "compatibility", + "mbstring", "polyfill", "portable", "shim" ], "support": { - "source": "https://github.com/symfony/polyfill-php80/tree/v1.29.0" + "source": "https://github.com/symfony/polyfill-mbstring/tree/v1.27.0" }, "funding": [ { @@ -1940,30 +2101,29 @@ "type": "tidelift" } ], - "time": "2024-01-29T20:11:03+00:00" + "time": "2022-11-03T14:55:06+00:00" }, { "name": "symfony/property-access", - "version": "v5.4.35", + "version": "v6.2.7", "source": { "type": "git", "url": "https://github.com/symfony/property-access.git", - "reference": "f1341758d8046cfff0ac748a0cad238f917191d4" + "reference": "5a389172011e2c37b47c896d0b156549126690a1" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/property-access/zipball/f1341758d8046cfff0ac748a0cad238f917191d4", - "reference": "f1341758d8046cfff0ac748a0cad238f917191d4", + "url": "https://api.github.com/repos/symfony/property-access/zipball/5a389172011e2c37b47c896d0b156549126690a1", + "reference": "5a389172011e2c37b47c896d0b156549126690a1", "shasum": "" }, "require": { - "php": ">=7.2.5", + "php": ">=8.1", "symfony/deprecation-contracts": "^2.1|^3", - "symfony/polyfill-php80": "^1.16", - "symfony/property-info": "^5.2|^6.0" + "symfony/property-info": "^5.4|^6.0" }, "require-dev": { - "symfony/cache": "^4.4|^5.0|^6.0" + "symfony/cache": "^5.4|^6.0" }, "suggest": { "psr/cache-implementation": "To cache access methods." @@ -2001,11 +2161,11 @@ "injection", "object", "property", - "property-path", + "property path", "reflection" ], "support": { - "source": "https://github.com/symfony/property-access/tree/v5.4.35" + "source": "https://github.com/symfony/property-access/tree/v6.2.7" }, "funding": [ { @@ -2021,40 +2181,38 @@ "type": "tidelift" } ], - "time": "2024-01-23T13:51:25+00:00" + "time": "2023-02-14T08:44:56+00:00" }, { "name": "symfony/property-info", - "version": "v5.4.35", + "version": "v6.2.7", "source": { "type": "git", "url": "https://github.com/symfony/property-info.git", - "reference": "d30d48f366ad2bfbf521256be85eb1c182c29198" + "reference": "5cf906918ea0f74032ffc5c0b85def246ce409df" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/property-info/zipball/d30d48f366ad2bfbf521256be85eb1c182c29198", - "reference": "d30d48f366ad2bfbf521256be85eb1c182c29198", + "url": "https://api.github.com/repos/symfony/property-info/zipball/5cf906918ea0f74032ffc5c0b85def246ce409df", + "reference": "5cf906918ea0f74032ffc5c0b85def246ce409df", "shasum": "" }, "require": { - "php": ">=7.2.5", - "symfony/deprecation-contracts": "^2.1|^3", - "symfony/polyfill-php80": "^1.16", - "symfony/string": "^5.1|^6.0" + "php": ">=8.1", + "symfony/string": "^5.4|^6.0" }, "conflict": { - "phpdocumentor/reflection-docblock": "<3.2.2", - "phpdocumentor/type-resolver": "<1.4.0", - "symfony/dependency-injection": "<4.4" + "phpdocumentor/reflection-docblock": "<5.2", + "phpdocumentor/type-resolver": "<1.5.1", + "symfony/dependency-injection": "<5.4" }, "require-dev": { "doctrine/annotations": "^1.10.4|^2", - "phpdocumentor/reflection-docblock": "^3.0|^4.0|^5.0", + "phpdocumentor/reflection-docblock": "^5.2", "phpstan/phpdoc-parser": "^1.0", - "symfony/cache": "^4.4|^5.0|^6.0", - "symfony/dependency-injection": "^4.4|^5.0|^6.0", - "symfony/serializer": "^4.4|^5.0|^6.0" + "symfony/cache": "^5.4|^6.0", + "symfony/dependency-injection": "^5.4|^6.0", + "symfony/serializer": "^5.4|^6.0" }, "suggest": { "phpdocumentor/reflection-docblock": "To use the PHPDoc", @@ -2096,7 +2254,7 @@ "validator" ], "support": { - "source": "https://github.com/symfony/property-info/tree/v5.4.35" + "source": "https://github.com/symfony/property-info/tree/v6.2.7" }, "funding": [ { @@ -2112,38 +2270,38 @@ "type": "tidelift" } ], - "time": "2024-01-23T15:43:50+00:00" + "time": "2023-02-14T08:53:37+00:00" }, { "name": "symfony/string", - "version": "v5.4.36", + "version": "v6.2.7", "source": { "type": "git", "url": "https://github.com/symfony/string.git", - "reference": "4e232c83622bd8cd32b794216aa29d0d266d353b" + "reference": "67b8c1eec78296b85dc1c7d9743830160218993d" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/string/zipball/4e232c83622bd8cd32b794216aa29d0d266d353b", - "reference": "4e232c83622bd8cd32b794216aa29d0d266d353b", + "url": "https://api.github.com/repos/symfony/string/zipball/67b8c1eec78296b85dc1c7d9743830160218993d", + "reference": "67b8c1eec78296b85dc1c7d9743830160218993d", "shasum": "" }, "require": { - "php": ">=7.2.5", + "php": ">=8.1", "symfony/polyfill-ctype": "~1.8", "symfony/polyfill-intl-grapheme": "~1.0", "symfony/polyfill-intl-normalizer": "~1.0", - "symfony/polyfill-mbstring": "~1.0", - "symfony/polyfill-php80": "~1.15" + "symfony/polyfill-mbstring": "~1.0" }, "conflict": { - "symfony/translation-contracts": ">=3.0" + "symfony/translation-contracts": "<2.0" }, "require-dev": { - "symfony/error-handler": "^4.4|^5.0|^6.0", - "symfony/http-client": "^4.4|^5.0|^6.0", - "symfony/translation-contracts": "^1.1|^2", - "symfony/var-exporter": "^4.4|^5.0|^6.0" + "symfony/error-handler": "^5.4|^6.0", + "symfony/http-client": "^5.4|^6.0", + "symfony/intl": "^6.2", + "symfony/translation-contracts": "^2.0|^3.0", + "symfony/var-exporter": "^5.4|^6.0" }, "type": "library", "autoload": { @@ -2182,7 +2340,7 @@ "utf8" ], "support": { - "source": "https://github.com/symfony/string/tree/v5.4.36" + "source": "https://github.com/symfony/string/tree/v6.2.7" }, "funding": [ { @@ -2198,26 +2356,26 @@ "type": "tidelift" } ], - "time": "2024-02-01T08:49:30+00:00" + "time": "2023-02-24T10:42:00+00:00" }, { "name": "tracy/tracy", - "version": "v2.10.7", + "version": "v2.9.7", "source": { "type": "git", "url": "https://github.com/nette/tracy.git", - "reference": "7e7b25ba103968d5318d37db330b2e9c755dc765" + "reference": "1c6e9b5bad030fdf49194154c9674201fa6372bb" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/tracy/zipball/7e7b25ba103968d5318d37db330b2e9c755dc765", - "reference": "7e7b25ba103968d5318d37db330b2e9c755dc765", + "url": "https://api.github.com/repos/nette/tracy/zipball/1c6e9b5bad030fdf49194154c9674201fa6372bb", + "reference": "1c6e9b5bad030fdf49194154c9674201fa6372bb", "shasum": "" }, "require": { "ext-json": "*", "ext-session": "*", - "php": ">=8.0 <8.4" + "php": ">=7.2 <8.3" }, "conflict": { "nette/di": "<3.0" @@ -2225,7 +2383,6 @@ "require-dev": { "latte/latte": "^2.5", "nette/di": "^3.0", - "nette/http": "^3.0", "nette/mail": "^3.0", "nette/tester": "^2.2", "nette/utils": "^3.0", @@ -2235,7 +2392,7 @@ "type": "library", "extra": { "branch-alias": { - "dev-master": "2.10-dev" + "dev-master": "2.9-dev" } }, "autoload": { @@ -2271,53 +2428,54 @@ ], "support": { "issues": "https://github.com/nette/tracy/issues", - "source": "https://github.com/nette/tracy/tree/v2.10.7" + "source": "https://github.com/nette/tracy/tree/v2.9.7" }, - "time": "2024-04-29T11:44:00+00:00" + "time": "2023-02-28T13:01:54+00:00" }, { "name": "ublaboo/datagrid", - "version": "v6.10.0", + "version": "dev-next", "source": { "type": "git", "url": "https://github.com/contributte/datagrid.git", - "reference": "1a63088529f47692d57c186f43a9e084f4b52e88" + "reference": "1aca86dbff52f13bd771ab6f3cbac003b28b605b" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/contributte/datagrid/zipball/1a63088529f47692d57c186f43a9e084f4b52e88", - "reference": "1a63088529f47692d57c186f43a9e084f4b52e88", + "url": "https://api.github.com/repos/contributte/datagrid/zipball/1aca86dbff52f13bd771ab6f3cbac003b28b605b", + "reference": "1aca86dbff52f13bd771ab6f3cbac003b28b605b", "shasum": "" }, "require": { "contributte/application": "^0.5.0", "nette/di": "^3.0.0", "nette/forms": "^3.1.3", - "nette/utils": "^3.0.1 || ^4.0.0", - "php": ">=7.2", - "symfony/property-access": "^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0" + "nette/utils": "^3.0.1", + "php": ">=8.0", + "symfony/property-access": "^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0" }, "require-dev": { - "contributte/code-rules": "^1.1.0", + "contributte/qa": "^0.3.0", "dibi/dibi": "^3.0.0 || ^4.0.0", "doctrine/annotations": "^1.12.1", "doctrine/cache": "^1.11.0", "doctrine/orm": "^2.11.1", - "elasticsearch/elasticsearch": "^7.1", + "elasticsearch/elasticsearch": "^8.6", "mockery/mockery": "^1.3.3", "nette/database": "^3.0.2", "nette/tester": "^2.3.4", - "nextras/dbal": "^3.0.1 || ^4.0", - "nextras/orm": "^3.1.0 || ^4.0", - "ninjify/coding-standard": "^0.12.1", + "nextras/dbal": "^4.0", + "nextras/orm": "^4.0", + "phpstan/phpstan-deprecation-rules": "^1.1", "phpstan/phpstan-nette": "^1.0.0", + "phpstan/phpstan-strict-rules": "^1.4", "tharos/leanmapper": "^3.4.2 || ^4.0.0", "tracy/tracy": "^2.6.3" }, "type": "library", "extra": { "branch-alias": { - "dev-master": "6.10.x-dev" + "dev-master": "7.x-dev" } }, "autoload": { @@ -2350,7 +2508,7 @@ ], "support": { "issues": "https://github.com/contributte/datagrid/issues", - "source": "https://github.com/contributte/datagrid/tree/v6.10.0" + "source": "https://github.com/contributte/datagrid/tree/next" }, "funding": [ { @@ -2362,41 +2520,42 @@ "type": "github" } ], - "time": "2024-03-03T16:52:06+00:00" + "time": "2023-03-07T15:24:33+00:00" } ], "packages-dev": [ { - "name": "dealerdirect/phpcodesniffer-composer-installer", - "version": "v0.7.2", + "name": "contributte/qa", + "version": "dev-master", "source": { "type": "git", - "url": "https://github.com/Dealerdirect/phpcodesniffer-composer-installer.git", - "reference": "1c968e542d8843d7cd71de3c5c9c3ff3ad71a1db" + "url": "https://github.com/contributte/qa.git", + "reference": "8ef95fed5ab32dc7bb2f87bed4c471ac1987a6ac" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/Dealerdirect/phpcodesniffer-composer-installer/zipball/1c968e542d8843d7cd71de3c5c9c3ff3ad71a1db", - "reference": "1c968e542d8843d7cd71de3c5c9c3ff3ad71a1db", + "url": "https://api.github.com/repos/contributte/qa/zipball/8ef95fed5ab32dc7bb2f87bed4c471ac1987a6ac", + "reference": "8ef95fed5ab32dc7bb2f87bed4c471ac1987a6ac", "shasum": "" }, "require": { - "composer-plugin-api": "^1.0 || ^2.0", - "php": ">=5.3", - "squizlabs/php_codesniffer": "^2.0 || ^3.1.0 || ^4.0" + "php": ">=8.0", + "slevomat/coding-standard": "^8.5.1", + "squizlabs/php_codesniffer": "^3.6.1" }, "require-dev": { - "composer/composer": "*", - "php-parallel-lint/php-parallel-lint": "^1.3.1", - "phpcompatibility/php-compatibility": "^9.0" + "contributte/tester": "^0.1.0", + "symfony/process": "^6.0.0" }, - "type": "composer-plugin", + "default-branch": true, + "bin": [ + "bin/codesniffer", + "bin/codefixer" + ], + "type": "library", "extra": { - "class": "Dealerdirect\\Composer\\Plugin\\Installers\\PHPCodeSniffer\\Plugin" - }, - "autoload": { - "psr-4": { - "Dealerdirect\\Composer\\Plugin\\Installers\\PHPCodeSniffer\\": "src/" + "branch-alias": { + "dev-master": "0.4.x-dev" } }, "notification-url": "https://packagist.org/downloads/", @@ -2405,65 +2564,84 @@ ], "authors": [ { - "name": "Franck Nijhof", - "email": "franck.nijhof@dealerdirect.com", - "homepage": "http://www.frenck.nl", - "role": "Developer / IT Manager" - }, - { - "name": "Contributors", - "homepage": "https://github.com/Dealerdirect/phpcodesniffer-composer-installer/graphs/contributors" + "name": "Milan Felix Šulc", + "homepage": "https://f3l1x.io" } ], - "description": "PHP_CodeSniffer Standards Composer Installer Plugin", - "homepage": "http://www.dealerdirect.com", + "description": "Tuned & very strict coding standards for PHP projects. Trusted by Contributte, Apitte, Nettrine and many others.", + "homepage": "https://github.com/contributte/qa", "keywords": [ - "PHPCodeSniffer", - "PHP_CodeSniffer", - "code quality", + "Codestyle", "codesniffer", - "composer", - "installer", - "phpcbf", - "phpcs", - "plugin", + "contributte", "qa", - "quality", - "standard", - "standards", - "style guide", - "stylecheck", - "tests" + "quality assurance" ], "support": { - "issues": "https://github.com/dealerdirect/phpcodesniffer-composer-installer/issues", - "source": "https://github.com/dealerdirect/phpcodesniffer-composer-installer" + "issues": "https://github.com/contributte/qa/issues", + "source": "https://github.com/contributte/qa/tree/master" }, - "time": "2022-02-04T12:51:07+00:00" + "funding": [ + { + "url": "https://contributte.org/partners.html", + "type": "custom" + }, + { + "url": "https://github.com/f3l1x", + "type": "github" + } + ], + "time": "2022-12-22T15:09:44+00:00" }, { - "name": "ninjify/coding-standard", - "version": "v0.12.1", + "name": "contributte/tester", + "version": "v0.1.0", "source": { "type": "git", - "url": "https://github.com/ninjify/coding-standard.git", - "reference": "c655eedbe1b4f9b307e9941ad347f9078fbdd58a" + "url": "https://github.com/contributte/tester.git", + "reference": "792373c8dc31be448cc4e9383e443a9ea713ce4b" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/ninjify/coding-standard/zipball/c655eedbe1b4f9b307e9941ad347f9078fbdd58a", - "reference": "c655eedbe1b4f9b307e9941ad347f9078fbdd58a", + "url": "https://api.github.com/repos/contributte/tester/zipball/792373c8dc31be448cc4e9383e443a9ea713ce4b", + "reference": "792373c8dc31be448cc4e9383e443a9ea713ce4b", "shasum": "" }, "require": { - "php": ">=7.2", - "slevomat/coding-standard": "^7.0.18", - "squizlabs/php_codesniffer": "^3.5.8" + "nette/tester": "^2.3.4", + "php": ">=7.4" + }, + "require-dev": { + "contributte/qa": "^0.1", + "janmarek/mockista": "^1.1.0", + "mockery/mockery": "^1.2.2", + "nette/di": "~3.0.0", + "nette/robot-loader": "^3.2", + "phpstan/phpstan": "^1.0", + "phpstan/phpstan-deprecation-rules": "^1.0", + "phpstan/phpstan-strict-rules": "^1.0" }, + "suggest": { + "janmarek/mockista": "to use BaseMockistaTestCase", + "mockery/mockery": "to use BaseMockeryTestCase", + "nette/di": "to use BaseContainerTestCase" + }, + "bin": [ + "bin/nunjuck", + "bin/nunjuck-setup" + ], "type": "library", "extra": { "branch-alias": { - "dev-master": "0.13.x-dev" + "dev-master": "0.1.x-dev" + } + }, + "autoload": { + "files": [ + "src/functions.php" + ], + "psr-4": { + "Contributte\\Tester\\": "src" } }, "notification-url": "https://packagist.org/downloads/", @@ -2476,17 +2654,16 @@ "homepage": "https://f3l1x.io" } ], - "description": "Tuned & very strict coding standards for PHP projects. Trusted by Contributte, Apitte, Nettrine and many others.", - "homepage": "https://github.com/ninjify/coding-standard", + "description": "Special tuned version of nette/tester for your PHP projects", + "homepage": "https://github.com/contributte/tester", "keywords": [ - "Codestyle", - "codesniffer", - "ninjify", - "php" + "nette", + "php", + "tester" ], "support": { - "issues": "https://github.com/ninjify/coding-standard/issues", - "source": "https://github.com/ninjify/coding-standard/tree/v0.12.1" + "issues": "https://github.com/contributte/tester/issues", + "source": "https://github.com/contributte/tester/tree/v0.1.0" }, "funding": [ { @@ -2498,36 +2675,42 @@ "type": "github" } ], - "time": "2022-02-11T14:34:15+00:00" + "time": "2022-01-29T12:08:32+00:00" }, { - "name": "ninjify/qa", - "version": "v0.13.0", + "name": "dealerdirect/phpcodesniffer-composer-installer", + "version": "v1.0.0", "source": { "type": "git", - "url": "https://github.com/ninjify/qa.git", - "reference": "9080dc0b8c28ba9b984e451f99654212288e60bb" + "url": "https://github.com/PHPCSStandards/composer-installer.git", + "reference": "4be43904336affa5c2f70744a348312336afd0da" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/ninjify/qa/zipball/9080dc0b8c28ba9b984e451f99654212288e60bb", - "reference": "9080dc0b8c28ba9b984e451f99654212288e60bb", + "url": "https://api.github.com/repos/PHPCSStandards/composer-installer/zipball/4be43904336affa5c2f70744a348312336afd0da", + "reference": "4be43904336affa5c2f70744a348312336afd0da", "shasum": "" }, "require": { - "ninjify/coding-standard": "^0.12.0", - "php": ">=7.2", - "php-parallel-lint/php-parallel-lint": "^1.2.0" + "composer-plugin-api": "^1.0 || ^2.0", + "php": ">=5.4", + "squizlabs/php_codesniffer": "^2.0 || ^3.1.0 || ^4.0" }, - "bin": [ - "bin/codesniffer", - "bin/codefixer", - "bin/linter" - ], - "type": "library", + "require-dev": { + "composer/composer": "*", + "ext-json": "*", + "ext-zip": "*", + "php-parallel-lint/php-parallel-lint": "^1.3.1", + "phpcompatibility/php-compatibility": "^9.0", + "yoast/phpunit-polyfills": "^1.0" + }, + "type": "composer-plugin", "extra": { - "branch-alias": { - "dev-master": "0.13.x-dev" + "class": "PHPCSStandards\\Composer\\Plugin\\Installers\\PHPCodeSniffer\\Plugin" + }, + "autoload": { + "psr-4": { + "PHPCSStandards\\Composer\\Plugin\\Installers\\PHPCodeSniffer\\": "src/" } }, "notification-url": "https://packagist.org/downloads/", @@ -2536,105 +2719,129 @@ ], "authors": [ { - "name": "Milan Felix Šulc", - "homepage": "https://f3l1x.io" + "name": "Franck Nijhof", + "email": "franck.nijhof@dealerdirect.com", + "homepage": "http://www.frenck.nl", + "role": "Developer / IT Manager" + }, + { + "name": "Contributors", + "homepage": "https://github.com/PHPCSStandards/composer-installer/graphs/contributors" } ], - "description": "Quality assurance for your PHP projects", - "homepage": "https://github.com/ninjify/qa", + "description": "PHP_CodeSniffer Standards Composer Installer Plugin", + "homepage": "http://www.dealerdirect.com", "keywords": [ - "assurance", + "PHPCodeSniffer", + "PHP_CodeSniffer", + "code quality", "codesniffer", - "linter", - "nette", - "php", - "quality" + "composer", + "installer", + "phpcbf", + "phpcs", + "plugin", + "qa", + "quality", + "standard", + "standards", + "style guide", + "stylecheck", + "tests" ], "support": { - "issues": "https://github.com/ninjify/qa/issues", - "source": "https://github.com/ninjify/qa/tree/v0.13.0" + "issues": "https://github.com/PHPCSStandards/composer-installer/issues", + "source": "https://github.com/PHPCSStandards/composer-installer" }, - "funding": [ - { - "url": "https://contributte.org/partners.html", - "type": "custom" - }, - { - "url": "https://github.com/f3l1x", - "type": "github" - } - ], - "time": "2022-01-08T13:15:44+00:00" + "time": "2023-01-05T11:28:13+00:00" }, { - "name": "php-parallel-lint/php-parallel-lint", - "version": "v1.3.2", + "name": "nette/tester", + "version": "v2.5.0", "source": { "type": "git", - "url": "https://github.com/php-parallel-lint/PHP-Parallel-Lint.git", - "reference": "6483c9832e71973ed29cf71bd6b3f4fde438a9de" + "url": "https://github.com/nette/tester.git", + "reference": "78555c76859208ee049335863e63e357ba71578f" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/php-parallel-lint/PHP-Parallel-Lint/zipball/6483c9832e71973ed29cf71bd6b3f4fde438a9de", - "reference": "6483c9832e71973ed29cf71bd6b3f4fde438a9de", + "url": "https://api.github.com/repos/nette/tester/zipball/78555c76859208ee049335863e63e357ba71578f", + "reference": "78555c76859208ee049335863e63e357ba71578f", "shasum": "" }, "require": { - "ext-json": "*", - "php": ">=5.3.0" - }, - "replace": { - "grogy/php-parallel-lint": "*", - "jakub-onderka/php-parallel-lint": "*" + "php": ">=8.0 <8.3" }, "require-dev": { - "nette/tester": "^1.3 || ^2.0", - "php-parallel-lint/php-console-highlighter": "0.* || ^1.0", - "squizlabs/php_codesniffer": "^3.6" - }, - "suggest": { - "php-parallel-lint/php-console-highlighter": "Highlight syntax in code snippet" + "ext-simplexml": "*", + "phpstan/phpstan": "^1.0" }, "bin": [ - "parallel-lint" + "src/tester" ], "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.5-dev" + } + }, "autoload": { "classmap": [ - "./src/" + "src/" ] }, "notification-url": "https://packagist.org/downloads/", "license": [ - "BSD-2-Clause" + "BSD-3-Clause", + "GPL-2.0-only", + "GPL-3.0-only" ], "authors": [ { - "name": "Jakub Onderka", - "email": "ahoj@jakubonderka.cz" + "name": "David Grudl", + "homepage": "https://davidgrudl.com" + }, + { + "name": "Miloslav Hůla", + "homepage": "https://github.com/milo" + }, + { + "name": "Nette Community", + "homepage": "https://nette.org/contributors" } ], - "description": "This tool check syntax of PHP files about 20x faster than serial check.", - "homepage": "https://github.com/php-parallel-lint/PHP-Parallel-Lint", + "description": "Nette Tester: enjoyable unit testing in PHP with code coverage reporter. 🍏🍏🍎🍏", + "homepage": "https://tester.nette.org", + "keywords": [ + "Xdebug", + "assertions", + "clover", + "code coverage", + "nette", + "pcov", + "phpdbg", + "phpunit", + "testing", + "unit" + ], "support": { - "issues": "https://github.com/php-parallel-lint/PHP-Parallel-Lint/issues", - "source": "https://github.com/php-parallel-lint/PHP-Parallel-Lint/tree/v1.3.2" + "issues": "https://github.com/nette/tester/issues", + "source": "https://github.com/nette/tester/tree/v2.5.0" }, - "time": "2022-02-21T12:50:22+00:00" + "time": "2023-03-02T02:14:46+00:00" }, { "name": "phpstan/phpdoc-parser", - "version": "1.4.5", + "version": "1.15.3", "source": { "type": "git", "url": "https://github.com/phpstan/phpdoc-parser.git", - "reference": "129a63b3bc7caeb593c224c41f420675e63cfefc" + "reference": "61800f71a5526081d1b5633766aa88341f1ade76" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpdoc-parser/zipball/129a63b3bc7caeb593c224c41f420675e63cfefc", - "reference": "129a63b3bc7caeb593c224c41f420675e63cfefc", + "url": "https://api.github.com/repos/phpstan/phpdoc-parser/zipball/61800f71a5526081d1b5633766aa88341f1ade76", + "reference": "61800f71a5526081d1b5633766aa88341f1ade76", "shasum": "" }, "require": { @@ -2644,6 +2851,7 @@ "php-parallel-lint/php-parallel-lint": "^1.2", "phpstan/extension-installer": "^1.0", "phpstan/phpstan": "^1.5", + "phpstan/phpstan-phpunit": "^1.1", "phpstan/phpstan-strict-rules": "^1.0", "phpunit/phpunit": "^9.5", "symfony/process": "^5.2" @@ -2663,22 +2871,22 @@ "description": "PHPDoc parser with support for nullable, intersection and generic types", "support": { "issues": "https://github.com/phpstan/phpdoc-parser/issues", - "source": "https://github.com/phpstan/phpdoc-parser/tree/1.4.5" + "source": "https://github.com/phpstan/phpdoc-parser/tree/1.15.3" }, - "time": "2022-04-22T11:11:01+00:00" + "time": "2022-12-20T20:56:55+00:00" }, { "name": "phpstan/phpstan", - "version": "1.10.67", + "version": "1.10.5", "source": { "type": "git", "url": "https://github.com/phpstan/phpstan.git", - "reference": "16ddbe776f10da6a95ebd25de7c1dbed397dc493" + "reference": "1fb6f494d82455151ecf15c5c191923f5d84324e" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpstan/zipball/16ddbe776f10da6a95ebd25de7c1dbed397dc493", - "reference": "16ddbe776f10da6a95ebd25de7c1dbed397dc493", + "url": "https://api.github.com/repos/phpstan/phpstan/zipball/1fb6f494d82455151ecf15c5c191923f5d84324e", + "reference": "1fb6f494d82455151ecf15c5c191923f5d84324e", "shasum": "" }, "require": { @@ -2707,11 +2915,8 @@ "static analysis" ], "support": { - "docs": "https://phpstan.org/user-guide/getting-started", - "forum": "https://github.com/phpstan/phpstan/discussions", "issues": "https://github.com/phpstan/phpstan/issues", - "security": "https://github.com/phpstan/phpstan/security/policy", - "source": "https://github.com/phpstan/phpstan-src" + "source": "https://github.com/phpstan/phpstan/tree/1.10.5" }, "funding": [ { @@ -2721,9 +2926,61 @@ { "url": "https://github.com/phpstan", "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/phpstan/phpstan", + "type": "tidelift" + } + ], + "time": "2023-03-07T16:48:45+00:00" + }, + { + "name": "phpstan/phpstan-deprecation-rules", + "version": "1.1.2", + "source": { + "type": "git", + "url": "https://github.com/phpstan/phpstan-deprecation-rules.git", + "reference": "bcc1e8cdf81c3da1a2ba9188ee94cd7e2a62e865" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpstan/phpstan-deprecation-rules/zipball/bcc1e8cdf81c3da1a2ba9188ee94cd7e2a62e865", + "reference": "bcc1e8cdf81c3da1a2ba9188ee94cd7e2a62e865", + "shasum": "" + }, + "require": { + "php": "^7.2 || ^8.0", + "phpstan/phpstan": "^1.10" + }, + "require-dev": { + "php-parallel-lint/php-parallel-lint": "^1.2", + "phpstan/phpstan-php-parser": "^1.1", + "phpstan/phpstan-phpunit": "^1.0", + "phpunit/phpunit": "^9.5" + }, + "type": "phpstan-extension", + "extra": { + "phpstan": { + "includes": [ + "rules.neon" + ] + } + }, + "autoload": { + "psr-4": { + "PHPStan\\": "src/" } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" ], - "time": "2024-04-16T07:22:02+00:00" + "description": "PHPStan rules for detecting usage of deprecated classes, methods, properties, constants and traits.", + "support": { + "issues": "https://github.com/phpstan/phpstan-deprecation-rules/issues", + "source": "https://github.com/phpstan/phpstan-deprecation-rules/tree/1.1.2" + }, + "time": "2023-01-17T16:14:21+00:00" }, { "name": "phpstan/phpstan-dibi", @@ -2782,16 +3039,16 @@ }, { "name": "phpstan/phpstan-nette", - "version": "1.2.9", + "version": "1.2.4", "source": { "type": "git", "url": "https://github.com/phpstan/phpstan-nette.git", - "reference": "0e3a6805917811d685e59bb83c2286315f2f6d78" + "reference": "9e083bb5befde7b73f9a12fc5bd223a7dcd63920" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpstan-nette/zipball/0e3a6805917811d685e59bb83c2286315f2f6d78", - "reference": "0e3a6805917811d685e59bb83c2286315f2f6d78", + "url": "https://api.github.com/repos/phpstan/phpstan-nette/zipball/9e083bb5befde7b73f9a12fc5bd223a7dcd63920", + "reference": "9e083bb5befde7b73f9a12fc5bd223a7dcd63920", "shasum": "" }, "require": { @@ -2807,7 +3064,6 @@ "nette/utils": "<2.3.0" }, "require-dev": { - "nette/application": "^3.0", "nette/forms": "^3.0", "nette/utils": "^2.3.0 || ^3.0.0", "nikic/php-parser": "^4.13.2", @@ -2838,27 +3094,27 @@ "description": "Nette Framework class reflection extension for PHPStan", "support": { "issues": "https://github.com/phpstan/phpstan-nette/issues", - "source": "https://github.com/phpstan/phpstan-nette/tree/1.2.9" + "source": "https://github.com/phpstan/phpstan-nette/tree/1.2.4" }, - "time": "2023-04-12T14:11:53+00:00" + "time": "2023-02-18T13:39:23+00:00" }, { "name": "phpstan/phpstan-strict-rules", - "version": "1.5.5", + "version": "1.5.0", "source": { "type": "git", "url": "https://github.com/phpstan/phpstan-strict-rules.git", - "reference": "2e193a07651a6f4be3baa44ddb21d822681f5918" + "reference": "b7dd96a5503919a43b3cd06a2dced9d4252492f2" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpstan-strict-rules/zipball/2e193a07651a6f4be3baa44ddb21d822681f5918", - "reference": "2e193a07651a6f4be3baa44ddb21d822681f5918", + "url": "https://api.github.com/repos/phpstan/phpstan-strict-rules/zipball/b7dd96a5503919a43b3cd06a2dced9d4252492f2", + "reference": "b7dd96a5503919a43b3cd06a2dced9d4252492f2", "shasum": "" }, "require": { "php": "^7.2 || ^8.0", - "phpstan/phpstan": "^1.10.60" + "phpstan/phpstan": "^1.10" }, "require-dev": { "nikic/php-parser": "^4.13.0", @@ -2887,43 +3143,43 @@ "description": "Extra strict and opinionated rules for PHPStan", "support": { "issues": "https://github.com/phpstan/phpstan-strict-rules/issues", - "source": "https://github.com/phpstan/phpstan-strict-rules/tree/1.5.5" + "source": "https://github.com/phpstan/phpstan-strict-rules/tree/1.5.0" }, - "time": "2024-04-19T15:12:26+00:00" + "time": "2023-02-21T10:17:10+00:00" }, { "name": "slevomat/coding-standard", - "version": "7.1", + "version": "8.8.0", "source": { "type": "git", "url": "https://github.com/slevomat/coding-standard.git", - "reference": "b521bd358b5f7a7d69e9637fd139e036d8adeb6f" + "reference": "59e25146a4ef0a7b194c5bc55b32dd414345db89" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/slevomat/coding-standard/zipball/b521bd358b5f7a7d69e9637fd139e036d8adeb6f", - "reference": "b521bd358b5f7a7d69e9637fd139e036d8adeb6f", + "url": "https://api.github.com/repos/slevomat/coding-standard/zipball/59e25146a4ef0a7b194c5bc55b32dd414345db89", + "reference": "59e25146a4ef0a7b194c5bc55b32dd414345db89", "shasum": "" }, "require": { - "dealerdirect/phpcodesniffer-composer-installer": "^0.6.2 || ^0.7", + "dealerdirect/phpcodesniffer-composer-installer": "^0.6.2 || ^0.7 || ^1.0", "php": "^7.2 || ^8.0", - "phpstan/phpdoc-parser": "^1.4.1", - "squizlabs/php_codesniffer": "^3.6.2" + "phpstan/phpdoc-parser": ">=1.15.2 <1.16.0", + "squizlabs/php_codesniffer": "^3.7.1" }, "require-dev": { - "phing/phing": "2.17.2", + "phing/phing": "2.17.4", "php-parallel-lint/php-parallel-lint": "1.3.2", - "phpstan/phpstan": "1.4.10|1.5.2", - "phpstan/phpstan-deprecation-rules": "1.0.0", - "phpstan/phpstan-phpunit": "1.0.0|1.1.0", - "phpstan/phpstan-strict-rules": "1.1.0", - "phpunit/phpunit": "7.5.20|8.5.21|9.5.19" + "phpstan/phpstan": "1.4.10|1.9.6", + "phpstan/phpstan-deprecation-rules": "1.1.1", + "phpstan/phpstan-phpunit": "1.0.0|1.3.3", + "phpstan/phpstan-strict-rules": "1.4.4", + "phpunit/phpunit": "7.5.20|8.5.21|9.5.27" }, "type": "phpcodesniffer-standard", "extra": { "branch-alias": { - "dev-master": "7.x-dev" + "dev-master": "8.x-dev" } }, "autoload": { @@ -2936,9 +3192,13 @@ "MIT" ], "description": "Slevomat Coding Standard for PHP_CodeSniffer complements Consistence Coding Standard by providing sniffs with additional checks.", + "keywords": [ + "dev", + "phpcs" + ], "support": { "issues": "https://github.com/slevomat/coding-standard/issues", - "source": "https://github.com/slevomat/coding-standard/tree/7.1" + "source": "https://github.com/slevomat/coding-standard/tree/8.8.0" }, "funding": [ { @@ -2950,20 +3210,20 @@ "type": "tidelift" } ], - "time": "2022-03-29T12:44:16+00:00" + "time": "2023-01-09T10:46:13+00:00" }, { "name": "squizlabs/php_codesniffer", - "version": "3.6.2", + "version": "3.7.2", "source": { "type": "git", "url": "https://github.com/squizlabs/PHP_CodeSniffer.git", - "reference": "5e4e71592f69da17871dba6e80dd51bce74a351a" + "reference": "ed8e00df0a83aa96acf703f8c2979ff33341f879" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/squizlabs/PHP_CodeSniffer/zipball/5e4e71592f69da17871dba6e80dd51bce74a351a", - "reference": "5e4e71592f69da17871dba6e80dd51bce74a351a", + "url": "https://api.github.com/repos/squizlabs/PHP_CodeSniffer/zipball/ed8e00df0a83aa96acf703f8c2979ff33341f879", + "reference": "ed8e00df0a83aa96acf703f8c2979ff33341f879", "shasum": "" }, "require": { @@ -2999,24 +3259,27 @@ "homepage": "https://github.com/squizlabs/PHP_CodeSniffer", "keywords": [ "phpcs", - "standards" + "standards", + "static analysis" ], "support": { "issues": "https://github.com/squizlabs/PHP_CodeSniffer/issues", "source": "https://github.com/squizlabs/PHP_CodeSniffer", "wiki": "https://github.com/squizlabs/PHP_CodeSniffer/wiki" }, - "time": "2021-12-12T21:44:58+00:00" + "time": "2023-02-22T23:07:41+00:00" } ], "aliases": [], "minimum-stability": "dev", - "stability-flags": [], + "stability-flags": { + "ublaboo/datagrid": 20 + }, "prefer-stable": true, "prefer-lowest": false, "platform": { - "php": ">= 8.0" + "php": ">= 8.1" }, "platform-dev": [], - "plugin-api-version": "2.6.0" + "plugin-api-version": "2.3.0" } From 5a542d0d6b8b4bed8ed270b97700cc285fc7e69b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:26:55 +0100 Subject: [PATCH 19/34] NPM: deps --- package-lock.json | 103 ++++++++++++++++++++++++++++++++++++++++++---- package.json | 18 ++++++-- 2 files changed, 110 insertions(+), 11 deletions(-) diff --git a/package-lock.json b/package-lock.json index ac92bb1..731f0ea 100644 --- a/package-lock.json +++ b/package-lock.json @@ -9,17 +9,27 @@ "version": "0.0.0", "license": "MIT", "dependencies": { - "@fortawesome/fontawesome-free": "^6.1.2", + "@fortawesome/fontawesome-free": "^6.3.0", + "bootstrap": "^4.4.1", + "bootstrap-datepicker": "^1.9", + "bootstrap-select": "^1.13", + "happy-inputs": "^2.0", + "jquery": "^3.5.0", + "jquery-ui-sortable": "^1.0", "naja": "^2.2.0", - "nette-forms": "^3.0.0" + "nette-forms": "^3.0.0", + "nette.ajax.js": "^2.3", + "popper.js": "^1.14.7", + "prismjs": "^1.29.0", + "ublaboo-datagrid": "^6.2.13" }, "devDependencies": { "autoprefixer": "^10.4.0", "vite": "^2.6.10" }, "engines": { - "node": ">=17", - "npm": ">=8.10" + "node": ">=18.0", + "npm": ">=9.0" } }, "node_modules/@babel/runtime": { @@ -50,9 +60,9 @@ } }, "node_modules/@fortawesome/fontawesome-free": { - "version": "6.2.1", - "resolved": "https://registry.npmjs.org/@fortawesome/fontawesome-free/-/fontawesome-free-6.2.1.tgz", - "integrity": "sha512-viouXhegu/TjkvYQoiRZK3aax69dGXxgEjpvZW81wIJdxm5Fnvp3VVIP4VHKqX4SvFw6qpmkILkD4RJWAdrt7A==", + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/@fortawesome/fontawesome-free/-/fontawesome-free-6.3.0.tgz", + "integrity": "sha512-qVtd5i1Cc7cdrqnTWqTObKQHjPWAiRwjUPaXObaeNPcy7+WKxJumGBx66rfSFgK6LNpIasVKkEgW8oyf0tmPLA==", "hasInstallScript": true, "engines": { "node": ">=6" @@ -91,6 +101,42 @@ "postcss": "^8.1.0" } }, + "node_modules/bootstrap": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-4.6.2.tgz", + "integrity": "sha512-51Bbp/Uxr9aTuy6ca/8FbFloBUJZLHwnhTcnjIeRn2suQWsWzcuJhGjKDB5eppVte/8oCdOL3VuwxvZDUggwGQ==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/twbs" + }, + { + "type": "opencollective", + "url": "https://opencollective.com/bootstrap" + } + ], + "peerDependencies": { + "jquery": "1.9.1 - 3", + "popper.js": "^1.16.1" + } + }, + "node_modules/bootstrap-datepicker": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/bootstrap-datepicker/-/bootstrap-datepicker-1.9.0.tgz", + "integrity": "sha512-9rYYbaVOheGYxjOr/+bJCmRPihfy+LkLSg4fIFMT9Od8WwWB/MB50w0JO1eBgKUMbb7PFHQD5uAfI3ArAxZRXA==", + "dependencies": { + "jquery": ">=1.7.1 <4.0.0" + } + }, + "node_modules/bootstrap-select": { + "version": "1.13.18", + "resolved": "https://registry.npmjs.org/bootstrap-select/-/bootstrap-select-1.13.18.tgz", + "integrity": "sha512-V1IzK4rxBq5FrJtkzSH6RmFLFBsjx50byFbfAf8jYyXROWs7ZpprGjdHeoyq2HSsHyjJhMMwjsQhRoYAfxCGow==", + "peerDependencies": { + "bootstrap": ">=3.0.0", + "jquery": "1.9.1 - 3" + } + }, "node_modules/browserslist": { "version": "4.21.4", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.21.4.tgz", @@ -539,6 +585,11 @@ "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", "dev": true }, + "node_modules/happy-inputs": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/happy-inputs/-/happy-inputs-2.1.0.tgz", + "integrity": "sha512-xv0ulEIUo/1DbuJbl0Rs+3MDy+D7BkDYA710Re1dpeX4mDnqA8+jTZacVNi/xELa2dCjxOkZB84oFAhxoRkRhQ==" + }, "node_modules/has": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", @@ -563,6 +614,16 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/jquery": { + "version": "3.6.3", + "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.6.3.tgz", + "integrity": "sha512-bZ5Sy3YzKo9Fyc8wH2iIQK4JImJ6R0GWI9kL1/k7Z91ZBNgkRXE6U0JfHIizZbort8ZunhSI3jw9I6253ahKfg==" + }, + "node_modules/jquery-ui-sortable": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/jquery-ui-sortable/-/jquery-ui-sortable-1.0.0.tgz", + "integrity": "sha512-7xAUWoEJ/jHoj48ei8CCUtiad2uM3ie3IR2b3KB0Mpmb54IbBxzVb5vtrj0zqtd0GNQDImx+BPZml9QmK2EL3w==" + }, "node_modules/naja": { "version": "2.5.0", "resolved": "https://registry.npmjs.org/naja/-/naja-2.5.0.tgz", @@ -588,6 +649,11 @@ "resolved": "https://registry.npmjs.org/nette-forms/-/nette-forms-3.3.1.tgz", "integrity": "sha512-UOmA3rF+FjpSci5CGmMtsy79PMWCcl0yyfyCd8YXVS+c68FAnVq3ref5qSxYFcwFynTqcPsYKhsNh8eYW5nVhQ==" }, + "node_modules/nette.ajax.js": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/nette.ajax.js/-/nette.ajax.js-2.3.0.tgz", + "integrity": "sha512-yuWyy+Fkk3bgrNBLu+TyhKquws9GgmJNDQ9rUWZ3NE2Y0OznzG6V+TWF841JD3/VMIU3SXCclceos7oRlpxfbw==" + }, "node_modules/node-releases": { "version": "2.0.8", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.8.tgz", @@ -615,6 +681,16 @@ "integrity": "sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==", "dev": true }, + "node_modules/popper.js": { + "version": "1.16.1", + "resolved": "https://registry.npmjs.org/popper.js/-/popper.js-1.16.1.tgz", + "integrity": "sha512-Wb4p1J4zyFTbM+u6WuO4XstYx4Ky9Cewe4DWrel7B0w6VVICvPwdOpotjzcf6eD8TsckVnIMNONQyPIUFOUbCQ==", + "deprecated": "You can find the new Popper v2 at @popperjs/core, this package is dedicated to the legacy v1", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/popperjs" + } + }, "node_modules/postcss": { "version": "8.4.21", "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.21.tgz", @@ -645,6 +721,14 @@ "integrity": "sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ==", "dev": true }, + "node_modules/prismjs": { + "version": "1.29.0", + "resolved": "https://registry.npmjs.org/prismjs/-/prismjs-1.29.0.tgz", + "integrity": "sha512-Kx/1w86q/epKcmte75LNrEoT+lX8pBpavuAbvJWRXar7Hz8jrtF+e3vY751p0R8H9HdArwaCTNDDzHg/ScJK1Q==", + "engines": { + "node": ">=6" + } + }, "node_modules/regenerator-runtime": { "version": "0.13.11", "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.11.tgz", @@ -703,6 +787,11 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/ublaboo-datagrid": { + "version": "6.9.1", + "resolved": "https://registry.npmjs.org/ublaboo-datagrid/-/ublaboo-datagrid-6.9.1.tgz", + "integrity": "sha512-b5oaMIJHKPat97xzBwC6BeN8QNSJH5rLzA4yU0SqFm5q4d0tJlsze6knPV0tWWjSV1Z+aaoTgVKX83l4XnZ4Xw==" + }, "node_modules/update-browserslist-db": { "version": "1.0.10", "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.0.10.tgz", diff --git a/package.json b/package.json index 788cf5f..0306e55 100644 --- a/package.json +++ b/package.json @@ -3,13 +3,23 @@ "version": "0.0.0", "license": "MIT", "engines": { - "npm": ">=8.10", - "node": ">=17" + "npm": ">=9.0", + "node": ">=18.0" }, "dependencies": { - "@fortawesome/fontawesome-free": "^6.1.2", + "@fortawesome/fontawesome-free": "^6.3.0", + "bootstrap": "^4.4.1", + "bootstrap-datepicker": "^1.9", + "bootstrap-select": "^1.13", + "happy-inputs": "^2.0", + "jquery": "^3.5.0", + "jquery-ui-sortable": "^1.0", "naja": "^2.2.0", - "nette-forms": "^3.0.0" + "nette-forms": "^3.0.0", + "nette.ajax.js": "^2.3", + "popper.js": "^1.14.7", + "prismjs": "^1.29.0", + "ublaboo-datagrid": "^6.2.13" }, "devDependencies": { "autoprefixer": "^10.4.0", From 0b861f37cf2be37c9b051e66370724f9d00da2d6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:27:21 +0100 Subject: [PATCH 20/34] Docker: update compose --- docker-compose.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/docker-compose.yml b/docker-compose.yml index 08bf5e3..b339e9c 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -1,4 +1,4 @@ -version: '3.3' +version: '3.6' services: web: @@ -6,7 +6,7 @@ services: volumes: - ./:/srv ports: - - 80:80 + - 8000:80 depends_on: - database environment: @@ -15,7 +15,7 @@ services: database: image: mariadb:latest volumes: - - .docker/db/init.sql:/docker-entrypoint-initdb.d/init.sql + - db/init.sql:/docker-entrypoint-initdb.d/init.sql ports: - 3306:3306 environment: From 14dc6459b2d4be3ac7074448c2462099b5195b9b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:27:26 +0100 Subject: [PATCH 21/34] Makefile: modernize --- Makefile | 67 ++++++++++++++++++++++++++++++++++++++++++++++---------- 1 file changed, 56 insertions(+), 11 deletions(-) diff --git a/Makefile b/Makefile index 5e6d2cf..b51660c 100644 --- a/Makefile +++ b/Makefile @@ -1,28 +1,43 @@ +# Include variables +include .env.dist +-include .env +export + ############################################################ # PROJECT ################################################## ############################################################ -.PHONY: project install setup clean - +.PHONY: project project: install setup -install: +.PHONY: install +install: install-php install-node + +.PHONY: install-php +install-php: composer install +.PHONY: install-node +install-node: + npm install + +.PHONY: setup setup: - mkdir -p temp temp/sessions log - chmod +0777 temp temp/sessions log + cp -n .env.example .env || true + mkdir -p var/log var/tmp var/tmp/sessions + chmod 0777 var/log var/tmp var/tmp/sessions +.PHONY: clean clean: - find temp -mindepth 1 ! -name '.gitignore' -type f,d -exec rm -rf {} + - find log -mindepth 1 ! -name '.gitignore' -type f,d -exec rm -rf {} + + find var/tmp -mindepth 1 ! -name '.gitignore' -type f,d -exec rm -rf {} + + find var/log -mindepth 1 ! -name '.gitignore' -type f,d -exec rm -rf {} + ############################################################ # DEVELOPMENT ############################################## ############################################################ -.PHONY: qa dev cs csf phpstan tests coverage dev build - +.PHONY: qa qa: cs phpstan +.PHONY: cs cs: ifdef GITHUB_ACTION vendor/bin/phpcs --standard=ruleset.xml --extensions=php,phpt --tab-width=4 --ignore=tests/tmp -q --report=checkstyle app tests | cs2pr @@ -30,15 +45,19 @@ else vendor/bin/phpcs --standard=ruleset.xml --extensions=php,phpt --tab-width=4 --ignore=tests/tmp --colors -nsp app tests endif +.PHONY: csf csf: vendor/bin/phpcbf --standard=ruleset.xml --extensions=php,phpt --tab-width=4 --ignore=tests/tmp --colors -nsp app tests +.PHONY: phpstan phpstan: vendor/bin/phpstan analyse -c phpstan.neon --memory-limit=512M +.PHONY: tests tests: vendor/bin/tester -s -p php --colors 1 -C tests/Cases +.PHONY: coverage coverage: ifdef GITHUB_ACTION vendor/bin/tester -s -p phpdbg --colors 1 -C --coverage coverage.xml --coverage-src app tests/Cases @@ -46,19 +65,45 @@ else vendor/bin/tester -s -p phpdbg --colors 1 -C --coverage coverage.html --coverage-src app tests/Cases endif +.PHONY: dev dev: NETTE_DEBUG=1 NETTE_ENV=dev php -S 0.0.0.0:8000 -t www +.PHONY: build build: - echo "BUILD OK" + npm run build + +.PHONY: watch +watch: + npm run watch ############################################################ # DEPLOYMENT ############################################### ############################################################ .PHONY: deploy - deploy: $(MAKE) clean $(MAKE) project $(MAKE) build $(MAKE) clean + +############################################################ +# DOCKER ################################################### +############################################################ +.PHONY: docker-up +docker-up: + docker compose up + +.PHONY: docker-mariadb +docker-mariadb: ## Spin MariaDB docker container + docker run \ + -it \ + --rm \ + -p 3306:3306 \ + -v $(CURDIR)/.docker/data/mariadb:/var/lib/mysql \ + -v $(CURDIR)/db/init.sql:/docker-entrypoint-initdb.d/init.sql \ + -e MYSQL_USER=${DB_USER} \ + -e MYSQL_PASSWORD=${DB_PASSWORD} \ + -e MYSQL_ROOT_PASSWORD=${DB_ROOT_PASSWORD} \ + -e MYSQL_DATABASE=${DB_DATABASE} \ + mariadb:10.11 From 462f85b8f54dbab6ba81adeaa9f68e05cff897b4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:27:36 +0100 Subject: [PATCH 22/34] Vite: proper settings --- vite.config.js | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/vite.config.js b/vite.config.js index c7700a8..ff622c9 100644 --- a/vite.config.js +++ b/vite.config.js @@ -5,7 +5,7 @@ export default defineConfig(({ mode }) => { const DEV = mode === 'development'; return { - publicDir: './public/static', + publicDir: './assets/public', resolve: { alias: { '@': resolve(__dirname, 'assets/js'), @@ -24,18 +24,19 @@ export default defineConfig(({ mode }) => { }, build: { manifest: true, - outDir: './public/dist/', - emptyOutDir: false, + assetsDir: '', + outDir: './www/dist/', + emptyOutDir: true, minify: DEV ? false : 'esbuild', rollupOptions: { output: { manualChunks: undefined, - chunkFileNames: DEV ? '[name].js' : '[name]-[hash].js', - entryFileNames: DEV ? '[name].js' : '[name].[hash].js', - assetFileNames: DEV ? '[name].[ext]' : '[name].[hash].[ext]', + chunkFileNames: '[name].js', // DEV ? '[name].js' : '[name]-[hash].js', + entryFileNames: '[name].js', // DEV ? '[name].js' : '[name].[hash].js', + assetFileNames: '[name].[ext]', // DEV ? '[name].[ext]' : '[name].[hash].[ext]', }, input: { - app: './assets/js/app.js' + app: './assets/js/main.js' } } }, From 9a9266773065fca4d81b88d77394c2627b73f23a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:27:48 +0100 Subject: [PATCH 23/34] App: based on nella --- app/Bootstrap.php | 31 ++++++----- app/Model/RouterFactory.php | 21 -------- app/Model/Utils/Types.php | 4 +- app/Presenters/AssetsPresenter.php | 34 ------------- app/Presenters/Error4xxPresenter.php | 35 ------------- app/Presenters/ErrorPresenter.php | 51 ------------------- app/UI/@Templates/@layout.latte | 44 ++++++++++++++++ app/UI/@Templates/parts/code.latte | 25 +++++++++ app/{Presenters => UI}/AbstractPresenter.php | 6 +-- .../Actions}/ActionsPresenter.php | 6 +-- .../Actions/Templates}/default.latte | 0 app/{Presenters => UI/Add}/AddPresenter.php | 6 +-- .../Add => UI/Add/Templates}/default.latte | 0 .../Columns}/ColumnsPresenter.php | 8 ++- .../Columns/Templates}/default.latte | 0 .../Templates}/grid/columnsEmojis.latte | 0 app/{Presenters => UI/Edit}/EditPresenter.php | 6 +-- .../Edit/Templates}/default.latte | 0 .../Export}/ExportPresenter.php | 6 +-- .../Export/Templates}/default.latte | 0 .../Filters}/FiltersPresenter.php | 6 +-- .../Filters/Templates}/default.latte | 0 .../GroupActions}/GroupActionsPresenter.php | 6 +-- .../GroupActions/Templates}/default.latte | 0 .../Home/HomePresenter.php} | 8 ++- .../Home/Templates}/default.latte | 0 .../ItemDetail}/ItemDetailPresenter.php | 8 ++- .../ItemDetail/Templates}/default.latte | 0 .../Templates}/grid/item-detail-grid.latte | 0 .../Localization}/LocalizationPresenter.php | 6 +-- .../Localization/Templates}/default.latte | 0 app/{Presenters => UI/Row}/RowPresenter.php | 6 +-- .../Row => UI/Row/Templates}/default.latte | 0 app/UI/TEmptyLayoutView.php | 25 --------- .../TreeView/Templates}/default.latte | 0 .../TreeView}/TreeViewPresenter.php | 8 ++- app/templates/Error/403.latte | 7 --- app/templates/Error/404.latte | 8 --- app/templates/Error/405.latte | 6 --- app/templates/Error/410.latte | 6 --- app/templates/Error/4xx.latte | 4 -- app/templates/Error/500.phtml | 27 ---------- app/templates/Error/503.phtml | 22 -------- app/templates/datagridFactoryCode.latte | 15 ------ 44 files changed, 117 insertions(+), 334 deletions(-) delete mode 100644 app/Model/RouterFactory.php delete mode 100644 app/Presenters/AssetsPresenter.php delete mode 100644 app/Presenters/Error4xxPresenter.php delete mode 100644 app/Presenters/ErrorPresenter.php create mode 100644 app/UI/@Templates/@layout.latte create mode 100644 app/UI/@Templates/parts/code.latte rename app/{Presenters => UI}/AbstractPresenter.php (86%) rename app/{Presenters => UI/Actions}/ActionsPresenter.php (96%) rename app/{templates/Actions => UI/Actions/Templates}/default.latte (100%) rename app/{Presenters => UI/Add}/AddPresenter.php (93%) rename app/{templates/Add => UI/Add/Templates}/default.latte (100%) rename app/{Presenters => UI/Columns}/ColumnsPresenter.php (95%) rename app/{templates/Basic => UI/Columns/Templates}/default.latte (100%) rename app/{templates/Columns => UI/Columns/Templates}/grid/columnsEmojis.latte (100%) rename app/{Presenters => UI/Edit}/EditPresenter.php (96%) rename app/{templates/Columns => UI/Edit/Templates}/default.latte (100%) rename app/{Presenters => UI/Export}/ExportPresenter.php (94%) rename app/{templates/Edit => UI/Export/Templates}/default.latte (100%) rename app/{Presenters => UI/Filters}/FiltersPresenter.php (95%) rename app/{templates/Export => UI/Filters/Templates}/default.latte (100%) rename app/{Presenters => UI/GroupActions}/GroupActionsPresenter.php (97%) rename app/{templates/Filters => UI/GroupActions/Templates}/default.latte (100%) rename app/{Presenters/BasicPresenter.php => UI/Home/HomePresenter.php} (85%) rename app/{templates/GroupActions => UI/Home/Templates}/default.latte (100%) rename app/{Presenters => UI/ItemDetail}/ItemDetailPresenter.php (79%) rename app/{templates/ItemDetail => UI/ItemDetail/Templates}/default.latte (100%) rename app/{templates/ItemDetail => UI/ItemDetail/Templates}/grid/item-detail-grid.latte (100%) rename app/{Presenters => UI/Localization}/LocalizationPresenter.php (95%) rename app/{templates/Localization => UI/Localization/Templates}/default.latte (100%) rename app/{Presenters => UI/Row}/RowPresenter.php (95%) rename app/{templates/Row => UI/Row/Templates}/default.latte (100%) delete mode 100644 app/UI/TEmptyLayoutView.php rename app/{templates/TreeView => UI/TreeView/Templates}/default.latte (100%) rename app/{Presenters => UI/TreeView}/TreeViewPresenter.php (94%) delete mode 100644 app/templates/Error/403.latte delete mode 100644 app/templates/Error/404.latte delete mode 100644 app/templates/Error/405.latte delete mode 100644 app/templates/Error/410.latte delete mode 100644 app/templates/Error/4xx.latte delete mode 100644 app/templates/Error/500.phtml delete mode 100644 app/templates/Error/503.phtml delete mode 100644 app/templates/datagridFactoryCode.latte diff --git a/app/Bootstrap.php b/app/Bootstrap.php index 40665ee..341631f 100644 --- a/app/Bootstrap.php +++ b/app/Bootstrap.php @@ -2,28 +2,27 @@ namespace App; -use Nette\Bootstrap\Configurator; +use Contributte\Bootstrap\ExtraConfigurator; +use Contributte\Nella\Boot\Bootloader; +use Contributte\Nella\Boot\Preset\NellaPreset; +use Nette\Application\Application; final class Bootstrap { - public static function boot(): Configurator + public static function boot(): ExtraConfigurator { - $configurator = new Configurator(); - - $configurator->setDebugMode(getenv('NETTE_DEBUG') === '1'); - $configurator->enableTracy(__DIR__ . '/../log'); - - $configurator->setTimeZone('Europe/Prague'); - $configurator->setTempDirectory(__DIR__ . '/../temp'); - - $configurator->addConfig(__DIR__ . '/../config/services.neon'); - - if (file_exists(__DIR__ . '/../config/local.neon')) { - $configurator->addConfig(__DIR__ . '/../config/local.neon'); - } + return Bootloader::create() + ->use(NellaPreset::create(__DIR__)) + ->boot(); + } - return $configurator; + public static function run(): void + { + self::boot() + ->createContainer() + ->getByType(Application::class) + ->run(); } } diff --git a/app/Model/RouterFactory.php b/app/Model/RouterFactory.php deleted file mode 100644 index 03bb51a..0000000 --- a/app/Model/RouterFactory.php +++ /dev/null @@ -1,21 +0,0 @@ -addRoute('[/]', 'Basic:default'); - $router->addRoute('_datagrid/css/', 'Assets:css'); - $router->addRoute('_datagrid/js/', 'Assets:js'); - - return $router; - } - -} diff --git a/app/Model/Utils/Types.php b/app/Model/Utils/Types.php index beaee72..185ad43 100644 --- a/app/Model/Utils/Types.php +++ b/app/Model/Utils/Types.php @@ -9,11 +9,11 @@ class Types public static function forceInt(mixed $input): int { - if (!is_int($input)) { + if (!is_numeric($input)) { throw new InvalidArgumentException(sprintf('Expect int, given %s.', gettype($input))); } - return $input; + return intval($input); } public static function forceNumber(mixed $input): float|int diff --git a/app/Presenters/AssetsPresenter.php b/app/Presenters/AssetsPresenter.php deleted file mode 100644 index 17ca8b9..0000000 --- a/app/Presenters/AssetsPresenter.php +++ /dev/null @@ -1,34 +0,0 @@ -sendResponse(new CallbackResponse(function (IRequest $request, IResponse $response) use ($file): void { - $response->addHeader('content-type', 'text/css; charset=utf-8'); - echo FileSystem::read($this->parameters->get('vendorDir') . '/ublaboo/datagrid/assets/' . $file); - })); - } - - public function actionJs(string $file): void - { - $this->sendResponse(new CallbackResponse(function (IRequest $request, IResponse $response) use ($file): void { - $response->addHeader('content-type', 'application/javascript; charset=utf-8'); - echo FileSystem::read($this->parameters->get('vendorDir') . '/ublaboo/datagrid/assets/' . $file); - })); - } - -} diff --git a/app/Presenters/Error4xxPresenter.php b/app/Presenters/Error4xxPresenter.php deleted file mode 100644 index eada95b..0000000 --- a/app/Presenters/Error4xxPresenter.php +++ /dev/null @@ -1,35 +0,0 @@ -getRequest() === null) { - throw new UnexpectedValueException(); - } - - if (!$this->getRequest()->isMethod(Request::FORWARD)) { - $this->error(); - } - } - - public function renderDefault(BadRequestException $exception): void - { - // load template 403.latte or 404.latte or ... 4xx.latte - $file = __DIR__ . '/templates/Error/' . $exception->getCode() . '.latte'; - $this->getTemplate()->setFile( - is_file($file) ? $file : __DIR__ . '/templates/Error/4xx.latte' - ); - } - -} diff --git a/app/Presenters/ErrorPresenter.php b/app/Presenters/ErrorPresenter.php deleted file mode 100644 index 3748044..0000000 --- a/app/Presenters/ErrorPresenter.php +++ /dev/null @@ -1,51 +0,0 @@ -logger = $logger; - } - - public function run(Request $request): Response - { - $e = $request->getParameter('exception'); - if ($e instanceof BadRequestException) { - // $this->logger->log("HTTP code {$e->getCode()}: {$e->getMessage()} in {$e->getFile()}:{$e->getLine()}", 'access'); - [$module, , $sep] = Helpers::splitName($request->getPresenterName()); - $errorPresenter = $module . $sep . 'Error4xx'; - - return new ForwardResponse($request->setPresenterName($errorPresenter)); - } - - $this->logger->log($e, ILogger::EXCEPTION); - - return new CallbackResponse( - static function (IRequest $httpRequest, IResponse $httpResponse): void { - if (preg_match('#^text/html(?:;|$)#', (string) $httpResponse->getHeader('Content-Type')) > 0) { - require __DIR__ . '/templates/Error/500.phtml'; - } - } - ); - } - -} diff --git a/app/UI/@Templates/@layout.latte b/app/UI/@Templates/@layout.latte new file mode 100644 index 0000000..0b4740b --- /dev/null +++ b/app/UI/@Templates/@layout.latte @@ -0,0 +1,44 @@ + + + + + + + + + + {ifset title}{include title|stripHtml} | {/ifset}DataGrid Sandbox + + + + + + + {snippet flashes} +
+
+ {$flash->message} +
+
+ {/snippet} + + + +
+
+ {include content} +
+
{include 'parts/code.latte'}
+
+ + diff --git a/app/UI/@Templates/parts/code.latte b/app/UI/@Templates/parts/code.latte new file mode 100644 index 0000000..4ef4250 --- /dev/null +++ b/app/UI/@Templates/parts/code.latte @@ -0,0 +1,25 @@ +
+
+ {var $reflection = new ReflectionClass($control)} + {var $presenterFile = basename($reflection->getFileName())} +   See the code below 👇 or see GitHub +
+ +
{include #code|trim}
+
+
+{define #code} + {php + $method = new ReflectionMethod($control, 'createComponentGrid'); + $filename = $method->getFileName(); + $start_line = $method->getStartLine() - 1; + $end_line = $method->getEndLine(); + $length = $end_line - $start_line; + + $source = file($filename); + $body = implode("", array_slice($source, $start_line, $length)); + $body = trim(preg_replace_callback('/^\t/m', function($i){ return ''; }, $body)); + } + {$body} + +{/define} diff --git a/app/Presenters/AbstractPresenter.php b/app/UI/AbstractPresenter.php similarity index 86% rename from app/Presenters/AbstractPresenter.php rename to app/UI/AbstractPresenter.php index 6abf37f..e5e0204 100644 --- a/app/Presenters/AbstractPresenter.php +++ b/app/UI/AbstractPresenter.php @@ -1,13 +1,13 @@ onChange[] = [$this, 'changeStatus']; $grid->addColumnText('emojis', 'Emojis (template)') - ->setTemplate(__DIR__ . '/../templates/Columns/grid/columnsEmojis.latte'); + ->setTemplate(__DIR__ . '/Templates/grid/columnsEmojis.latte'); $grid->addColumnDateTime('birth_date', 'Birthday') ->setFormat('j. n. Y') diff --git a/app/templates/Basic/default.latte b/app/UI/Columns/Templates/default.latte similarity index 100% rename from app/templates/Basic/default.latte rename to app/UI/Columns/Templates/default.latte diff --git a/app/templates/Columns/grid/columnsEmojis.latte b/app/UI/Columns/Templates/grid/columnsEmojis.latte similarity index 100% rename from app/templates/Columns/grid/columnsEmojis.latte rename to app/UI/Columns/Templates/grid/columnsEmojis.latte diff --git a/app/Presenters/EditPresenter.php b/app/UI/Edit/EditPresenter.php similarity index 96% rename from app/Presenters/EditPresenter.php rename to app/UI/Edit/EditPresenter.php index 7299941..3b2b3a7 100644 --- a/app/Presenters/EditPresenter.php +++ b/app/UI/Edit/EditPresenter.php @@ -1,9 +1,9 @@ setItemsDetail(); - $grid->setTemplateFile(__DIR__ . '/../templates/ItemDetail/grid/item-detail-grid.latte'); + $grid->setTemplateFile(__DIR__ . '/Templates/grid/item-detail-grid.latte'); return $grid; } diff --git a/app/templates/ItemDetail/default.latte b/app/UI/ItemDetail/Templates/default.latte similarity index 100% rename from app/templates/ItemDetail/default.latte rename to app/UI/ItemDetail/Templates/default.latte diff --git a/app/templates/ItemDetail/grid/item-detail-grid.latte b/app/UI/ItemDetail/Templates/grid/item-detail-grid.latte similarity index 100% rename from app/templates/ItemDetail/grid/item-detail-grid.latte rename to app/UI/ItemDetail/Templates/grid/item-detail-grid.latte diff --git a/app/Presenters/LocalizationPresenter.php b/app/UI/Localization/LocalizationPresenter.php similarity index 95% rename from app/Presenters/LocalizationPresenter.php rename to app/UI/Localization/LocalizationPresenter.php index 174d71a..e1a6e31 100644 --- a/app/Presenters/LocalizationPresenter.php +++ b/app/UI/Localization/LocalizationPresenter.php @@ -1,9 +1,9 @@ getRequest(); - - if ($request !== null && $request->getParameter('inFrame') === true) { - $this->setLayout(__DIR__ . '/../templates/@layout.inFrame.latte'); - } - } - -} diff --git a/app/templates/TreeView/default.latte b/app/UI/TreeView/Templates/default.latte similarity index 100% rename from app/templates/TreeView/default.latte rename to app/UI/TreeView/Templates/default.latte diff --git a/app/Presenters/TreeViewPresenter.php b/app/UI/TreeView/TreeViewPresenter.php similarity index 94% rename from app/Presenters/TreeViewPresenter.php rename to app/UI/TreeView/TreeViewPresenter.php index 9a582a7..474d0d9 100644 --- a/app/Presenters/TreeViewPresenter.php +++ b/app/UI/TreeView/TreeViewPresenter.php @@ -1,8 +1,8 @@ where('c.parent_category_id = ?', $parentCategoryId); } - public function handleSort(int $itemId, int $prevId, int $nextId, int $parentId): void + public function handleSort(?int $itemId, ?int $prevId, ?int $nextId, ?int $parentId): void { $this->flashMessage( sprintf( diff --git a/app/templates/Error/403.latte b/app/templates/Error/403.latte deleted file mode 100644 index de00328..0000000 --- a/app/templates/Error/403.latte +++ /dev/null @@ -1,7 +0,0 @@ -{block content} -

Access Denied

- -

You do not have permission to view this page. Please try contact the web -site administrator if you believe you should be able to view this page.

- -

error 403

diff --git a/app/templates/Error/404.latte b/app/templates/Error/404.latte deleted file mode 100644 index 022001c..0000000 --- a/app/templates/Error/404.latte +++ /dev/null @@ -1,8 +0,0 @@ -{block content} -

Page Not Found

- -

The page you requested could not be found. It is possible that the address is -incorrect, or that the page no longer exists. Please use a search engine to find -what you are looking for.

- -

error 404

diff --git a/app/templates/Error/405.latte b/app/templates/Error/405.latte deleted file mode 100644 index d424892..0000000 --- a/app/templates/Error/405.latte +++ /dev/null @@ -1,6 +0,0 @@ -{block content} -

Method Not Allowed

- -

The requested method is not allowed for the URL.

- -

error 405

diff --git a/app/templates/Error/410.latte b/app/templates/Error/410.latte deleted file mode 100644 index 99bde92..0000000 --- a/app/templates/Error/410.latte +++ /dev/null @@ -1,6 +0,0 @@ -{block content} -

Page Not Found

- -

The page you requested has been taken off the site. We apologize for the inconvenience.

- -

error 410

diff --git a/app/templates/Error/4xx.latte b/app/templates/Error/4xx.latte deleted file mode 100644 index d5ce82f..0000000 --- a/app/templates/Error/4xx.latte +++ /dev/null @@ -1,4 +0,0 @@ -{block content} -

Oops...

- -

Your browser sent a request that this server could not understand or process.

diff --git a/app/templates/Error/500.phtml b/app/templates/Error/500.phtml deleted file mode 100644 index a2b900c..0000000 --- a/app/templates/Error/500.phtml +++ /dev/null @@ -1,27 +0,0 @@ - - - -Server Error - - - -
-
-

Server Error

- -

We're sorry! The server encountered an internal error and - was unable to complete your request. Please try again later.

- -

error 500

-
-
- - diff --git a/app/templates/Error/503.phtml b/app/templates/Error/503.phtml deleted file mode 100644 index 1c2c427..0000000 --- a/app/templates/Error/503.phtml +++ /dev/null @@ -1,22 +0,0 @@ - - - - - - - - -Site is temporarily down for maintenance - -

We're Sorry

- -

The site is temporarily down for maintenance. Please try again in a few minutes.

diff --git a/app/templates/datagridFactoryCode.latte b/app/templates/datagridFactoryCode.latte deleted file mode 100644 index 4f59b3f..0000000 --- a/app/templates/datagridFactoryCode.latte +++ /dev/null @@ -1,15 +0,0 @@ -{** - * @param $method - *} -{php - $method = new ReflectionMethod($control, $method); - $filename = $method->getFileName(); - $start_line = $method->getStartLine() - 1; - $end_line = $method->getEndLine(); - $length = $end_line - $start_line; - - $source = file($filename); - $body = implode("", array_slice($source, $start_line, $length)); - $body = trim(preg_replace_callback('/^\t/m', function($i){ return ''; }, $body)); -} -{$body} From 08cfecc95c80cad50ff76c36586910e562a4b34a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:28:00 +0100 Subject: [PATCH 24/34] Config: simplify --- config/config.neon | 35 +++++++++++++++++++++++++++++++++++ config/local.neon.dist | 9 +++++++++ config/local.neon.example | 3 --- config/services.neon | 28 ---------------------------- 4 files changed, 44 insertions(+), 31 deletions(-) create mode 100644 config/config.neon create mode 100644 config/local.neon.dist delete mode 100644 config/local.neon.example delete mode 100644 config/services.neon diff --git a/config/config.neon b/config/config.neon new file mode 100644 index 0000000..607352e --- /dev/null +++ b/config/config.neon @@ -0,0 +1,35 @@ +# ====================================== +# Config =============================== +php: + date.timezone: Europe/Prague + # session.save_path: %tempDir%/session + +# ====================================== +# Extension ============================ +extensions: + dibi: Dibi\Bridges\Nette\DibiExtension22 + +latte: + extensions: + - Latte\Essential\RawPhpExtension + +dibi: + host: %db.host% + username: %db.username% + password: %db.password% + database: %db.database% + port: %db.port% + +session: + savePath: "%tempDir%/sessions" + + +# ====================================== +# Parameters =========================== +parameters: + vendorDir: %appDir%/../vendor + +# ====================================== +# Services ============================= +services: + parameters: App\Model\Parameters(%parameters%) diff --git a/config/local.neon.dist b/config/local.neon.dist new file mode 100644 index 0000000..8af8359 --- /dev/null +++ b/config/local.neon.dist @@ -0,0 +1,9 @@ +parameters: + db: + host: database + username: contributte + password: contributte + database: contributte + port: 3306 + +services: diff --git a/config/local.neon.example b/config/local.neon.example deleted file mode 100644 index 12b6ebf..0000000 --- a/config/local.neon.example +++ /dev/null @@ -1,3 +0,0 @@ -parameters: - -services: diff --git a/config/services.neon b/config/services.neon deleted file mode 100644 index 8024ac3..0000000 --- a/config/services.neon +++ /dev/null @@ -1,28 +0,0 @@ -application: - errorPresenter: Error - mapping: - *: App\*Module\Presenters\*Presenter - -services: - router: App\Model\RouterFactory::create - parameters: App\Model\Parameters(%parameters%) - -extensions: - dibi: Dibi\Bridges\Nette\DibiExtension22 - -latte: - extensions: - - Latte\Essential\RawPhpExtension - -dibi: - host: database - username: contributte - password: contributte - database: contributte - port: 3306 - -session: - savePath: "%tempDir%/sessions" - -parameters: - vendorDir: %appDir%/../vendor From 69c6c588a4694a9e5d78302b7066803efda7654b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:28:09 +0100 Subject: [PATCH 25/34] DB: introduce db folder --- {.docker/db => db}/init.sql | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename {.docker/db => db}/init.sql (100%) diff --git a/.docker/db/init.sql b/db/init.sql similarity index 100% rename from .docker/db/init.sql rename to db/init.sql From a955b375aed63d9eb78867d79dbf81ec0de132c4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:28:16 +0100 Subject: [PATCH 26/34] App: introduce var folder --- {log => var/log}/.gitignore | 0 {temp => var/tmp}/.gitignore | 0 2 files changed, 0 insertions(+), 0 deletions(-) rename {log => var/log}/.gitignore (100%) rename {temp => var/tmp}/.gitignore (100%) diff --git a/log/.gitignore b/var/log/.gitignore similarity index 100% rename from log/.gitignore rename to var/log/.gitignore diff --git a/temp/.gitignore b/var/tmp/.gitignore similarity index 100% rename from temp/.gitignore rename to var/tmp/.gitignore From d966e27ac95457ce4400a730931420ba88f75ae3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:28:37 +0100 Subject: [PATCH 27/34] Assets: rewrite --- assets/css/main.css | 10 + {www/assets => assets/css}/styles.css | 0 assets/js/datagrid/datagrid.js | 922 ++++++++++++++++++++++ assets/js/datagrid/instant-url-refresh.js | 30 + assets/js/datagrid/spinners.js | 89 +++ assets/js/main.js | 26 + {www => assets/public}/favicon.ico | Bin www/assets/prism.css | 126 --- www/assets/prism.js | 10 - www/assets/scripts.js | 28 - www/index.php | 12 +- www/package-lock.json | 60 -- www/package.json | 16 - www/phpinfo.php | 2 - 14 files changed, 1079 insertions(+), 252 deletions(-) create mode 100644 assets/css/main.css rename {www/assets => assets/css}/styles.css (100%) create mode 100644 assets/js/datagrid/datagrid.js create mode 100644 assets/js/datagrid/instant-url-refresh.js create mode 100644 assets/js/datagrid/spinners.js create mode 100644 assets/js/main.js rename {www => assets/public}/favicon.ico (100%) delete mode 100644 www/assets/prism.css delete mode 100644 www/assets/prism.js delete mode 100644 www/assets/scripts.js delete mode 100644 www/package-lock.json delete mode 100644 www/package.json delete mode 100644 www/phpinfo.php diff --git a/assets/css/main.css b/assets/css/main.css new file mode 100644 index 0000000..cbfe77f --- /dev/null +++ b/assets/css/main.css @@ -0,0 +1,10 @@ +@import "@fortawesome/fontawesome-free/css/all.css"; +@import 'bootstrap/dist/css/bootstrap.css'; +@import 'bootstrap-datepicker/dist/css/bootstrap-datepicker.css'; +@import 'bootstrap-select/dist/css/bootstrap-select.css'; +@import 'ublaboo-datagrid/assets/datagrid.css'; +@import 'ublaboo-datagrid/assets/datagrid-spinners.css'; +@import 'prismjs/themes/prism-okaidia.css'; + +/* App styles */ +@import './styles.css'; diff --git a/www/assets/styles.css b/assets/css/styles.css similarity index 100% rename from www/assets/styles.css rename to assets/css/styles.css diff --git a/assets/js/datagrid/datagrid.js b/assets/js/datagrid/datagrid.js new file mode 100644 index 0000000..29a5206 --- /dev/null +++ b/assets/js/datagrid/datagrid.js @@ -0,0 +1,922 @@ +var dataGridRegisterExtension, dataGridRegisterAjaxCall, dataGridLoad, dataGridSubmitForm; + +if (typeof naja !== "undefined") { + var isNaja2 = function () { return naja && naja.VERSION && naja.VERSION >= 2 }; + var najaEventParams = function (params) { return isNaja2() ? params.detail : params }; + var najaRequest = function (params) { return isNaja2() ? params.detail.request : params.xhr }; + dataGridRegisterExtension = function (name, extension) { + var init = extension.init; + var success = extension.success; + var before = extension.before; + var complete = extension.complete; + var interaction = extension.interaction; + + + var NewExtension = function NewExtension(naja, name) { + this.name = name; + + this.initialize = function (naja) { + if(init) { + naja.addEventListener('init', function (params) { + init(najaEventParams(params).defaultOptions); + }); + } + + if(success) { + naja.addEventListener('success', function (params) { + var payload = isNaja2() ? params.detail.payload : params.response; + success(payload, najaEventParams(params).options); + }); + } + + var interactionTarget = naja; + if (isNaja2()) { + interactionTarget = interactionTarget.uiHandler; + } + + interactionTarget.addEventListener('interaction', function (params) { + if (isNaja2()) { + params.detail.options.nette = { + el: $(params.detail.element) + } + } else { + params.options.nette = { + el: $(params.element) + } + } + if (interaction) { + if (!interaction(najaEventParams(params).options)){ + params.preventDefault(); + } + } + }); + + if(before) { + naja.addEventListener('before', function (params) { + if (!before(najaRequest(params), najaEventParams(params).options)) + params.preventDefault(); + }); + } + + if(complete) { + naja.addEventListener('complete', function (params) { + complete(najaRequest(params), najaEventParams(params).options); + }); + } + } + if (!isNaja2()) { + this.initialize(naja); + } + return this; + } + + if (isNaja2()) { + naja.registerExtension(new NewExtension(null, name)); + } else { + naja.registerExtension(NewExtension, name); + } + }; + + + dataGridRegisterAjaxCall = function (params) { + var method = params.type || 'GET'; + var data = params.data || null; + + naja.makeRequest(method, params.url, data, {}) + .then(params.success) + .catch(params.error); + }; + + dataGridLoad = function () { + naja.load(); + }; + + dataGridSubmitForm = function (form) { + return naja.uiHandler.submitForm(form.get(0)); + }; +} else if ($.nette) { + dataGridRegisterExtension = function (name, extension) { + $.nette.ext(name, extension); + }; + dataGridRegisterAjaxCall = function (params) { + $.nette.ajax(params); + }; + dataGridLoad = function () { + $.nette.load(); + }; + dataGridSubmitForm = function (form) { + return form.submit(); + }; +} else { + throw new Error("Include Naja.js or nette.ajax for datagrids to work!") +} + + +var datagridFilterMultiSelect, datagridGroupActionMultiSelect, datagridShiftGroupSelection, datagridSortable, datagridSortableTree, getEventDomPath, + indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (i in this && this[i] === item) return i; } return -1; }; + +$(document).on('click', '[data-datagrid-confirm]:not(.ajax)', function(e) { + if (!confirm($(e.target).closest('a').attr('data-datagrid-confirm'))) { + e.stopPropagation(); + return e.preventDefault(); + } +}); + +if (typeof naja !== "undefined") { + dataGridRegisterExtension('datagrid.confirm', { + interaction: function(settings) { + var confirm_message; + if (settings.nette) { + confirm_message = settings.nette.el.data('datagrid-confirm'); + if (confirm_message) { + return confirm(confirm_message); + } + } + return true; + } + }); +} else { + dataGridRegisterExtension('datagrid.confirm', { + before: function(xhr, settings) { + var confirm_message; + if (settings.nette) { + confirm_message = settings.nette.el.data('datagrid-confirm'); + if (confirm_message) { + return confirm(confirm_message); + } + } + return true; + } + }); +} + + +$(document).on('change', 'select[data-autosubmit-per-page]', function() { + var button; + button = $(this).parent().find('input[type=submit]'); + if (button.length === 0) { + button = $(this).parent().find('button[type=submit]'); + } + return button.click(); +}).on('change', 'select[data-autosubmit]', function() { + return dataGridSubmitForm($(this).closest('form').first()); +}).on('change', 'input[data-autosubmit][data-autosubmit-change]', function(e) { + var $this, code; + code = e.which || e.keyCode || 0; + clearTimeout(window.datagrid_autosubmit_timer); + $this = $(this); + return window.datagrid_autosubmit_timer = setTimeout((function(_this) { + return function() { + return dataGridSubmitForm($this.closest('form').first()); + }; + })(this), 200); +}).on('keyup', 'input[data-autosubmit]', function(e) { + var $this, code; + code = e.which || e.keyCode || 0; + if ((code !== 13) && ((code >= 9 && code <= 40) || (code >= 112 && code <= 123))) { + return; + } + clearTimeout(window.datagrid_autosubmit_timer); + $this = $(this); + return window.datagrid_autosubmit_timer = setTimeout((function(_this) { + return function() { + return dataGridSubmitForm($this.closest('form').first()); + }; + })(this), 200); +}).on('keydown', '.datagrid-inline-edit input', function(e) { + var code; + code = e.which || e.keyCode || 0; + if (code === 13) { + e.stopPropagation(); + e.preventDefault(); + return $(this).closest('tr').find('.col-action-inline-edit [name="inline_edit[submit]"]').click(); + } +}); + +$(document).on('keydown', 'input[data-datagrid-manualsubmit]', function(e) { + var code; + code = e.which || e.keyCode || 0; + if (code === 13) { + e.stopPropagation(); + e.preventDefault(); + return dataGridSubmitForm($(this).closest('form').first()); + } +}); + +getEventDomPath = function(e) { + var node, path; + if (indexOf.call(e, path) >= 0) { + return e.path; + } + path = []; + node = e.target; + while (node !== document.body) { + if (node === null) { + break; + } + path.push(node); + node = node.parentNode; + } + return path; +}; + +datagridShiftGroupSelection = function() { + var last_checkbox; + last_checkbox = null; + return document.addEventListener('click', function(e) { + var checkboxes_rows, current_checkbox_row, el, event, i, ie, input, j, k, last_checkbox_row, last_checkbox_tbody, len, len1, len2, ref, ref1, results, row, rows; + ref = getEventDomPath(e); + for (i = 0, len = ref.length; i < len; i++) { + el = ref[i]; + if ($(el).is('.col-checkbox') && last_checkbox && e.shiftKey) { + current_checkbox_row = $(el).closest('tr'); + last_checkbox_row = last_checkbox.closest('tr'); + last_checkbox_tbody = last_checkbox_row.closest('tbody'); + checkboxes_rows = last_checkbox_tbody.find('tr').toArray(); + if (current_checkbox_row.index() > last_checkbox_row.index()) { + rows = checkboxes_rows.slice(last_checkbox_row.index(), current_checkbox_row.index()); + } else if (current_checkbox_row.index() < last_checkbox_row.index()) { + rows = checkboxes_rows.slice(current_checkbox_row.index() + 1, last_checkbox_row.index()); + } + if (!rows) { + return; + } + for (j = 0, len1 = rows.length; j < len1; j++) { + row = rows[j]; + input = $(row).find('.col-checkbox input[type=checkbox]')[0]; + if (input) { + input.checked = true; + ie = window.navigator.userAgent.indexOf("MSIE "); + if (ie) { + event = document.createEvent('Event'); + event.initEvent('change', true, true); + } else { + event = new Event('change', { + 'bubbles': true + }); + } + input.dispatchEvent(event); + } + } + } + } + ref1 = getEventDomPath(e); + results = []; + for (k = 0, len2 = ref1.length; k < len2; k++) { + el = ref1[k]; + if ($(el).is('.col-checkbox')) { + results.push(last_checkbox = $(el)); + } else { + results.push(void 0); + } + } + return results; + }); +}; + +datagridShiftGroupSelection(); + +document.addEventListener('change', function(e) { + var buttons, checked_inputs, counter, event, grid, i, ie, input, inputs, len, results, select, total; + grid = e.target.getAttribute('data-check'); + if (grid) { + checked_inputs = document.querySelectorAll('input[data-check-all-' + grid + ']:checked'); + select = document.querySelector('.datagrid-' + grid + ' select[name="group_action[group_action]"]'); + buttons = document.querySelectorAll('.datagrid-' + grid + ' .row-group-actions *[type="submit"]'); + counter = document.querySelector('.datagrid-' + grid + ' .datagrid-selected-rows-count'); + + if (checked_inputs.length) { + if (buttons) { + buttons.forEach(function (button) { + button.disabled = false; + }); + } + if (select) { + select.disabled = false; + } + total = document.querySelectorAll('input[data-check-all-' + grid + ']').length; + if (counter) { + counter.innerHTML = checked_inputs.length + '/' + total; + } + } else { + if (buttons) { + buttons.forEach(function (button) { + button.disabled = true; + }); + } + if (select) { + select.disabled = true; + select.value = ""; + } + if (counter) { + counter.innerHTML = ""; + } + } + ie = window.navigator.userAgent.indexOf("MSIE "); + if (ie) { + event = document.createEvent('Event'); + event.initEvent('change', true, true); + } else { + event = new Event('change', { + 'bubbles': true + }); + } + if (select) { + select.dispatchEvent(event); + } + } + grid = e.target.getAttribute('data-check-all'); + if (grid) { + inputs = document.querySelectorAll('input[type=checkbox][data-check-all-' + grid + ']'); + results = []; + for (i = 0, len = inputs.length; i < len; i++) { + input = inputs[i]; + input.checked = e.target.checked; + ie = window.navigator.userAgent.indexOf("MSIE "); + if (ie) { + event = document.createEvent('Event'); + event.initEvent('change', true, true); + } else { + event = new Event('change', { + 'bubbles': true + }); + } + results.push(input.dispatchEvent(event)); + } + return results; + } +}); + + +window.datagridSerializeUrl = function(obj, prefix) { + var str = []; + for(var p in obj) { + if (obj.hasOwnProperty(p)) { + var k = prefix ? prefix + "[" + p + "]" : p, v = obj[p]; + if (v !== null && v !== "") { + if (typeof v == "object") { + var r = window.datagridSerializeUrl(v, k); + if (r) { + str.push(r); + } + } else { + str.push(encodeURIComponent(k) + "=" + encodeURIComponent(v)); + } + } + } + } + return str.join("&"); +} +; + +datagridSortable = function() { + if (typeof $.fn.sortable === 'undefined') { + return; + } + return $('.datagrid [data-sortable]').sortable({ + handle: '.handle-sort', + items: 'tr', + axis: 'y', + update: function(event, ui) { + var component_prefix, data, item_id, next_id, prev_id, row, url; + row = ui.item.closest('tr[data-id]'); + item_id = row.data('id'); + prev_id = null; + next_id = null; + if (row.prev().length) { + prev_id = row.prev().data('id'); + } + if (row.next().length) { + next_id = row.next().data('id'); + } + url = $(this).data('sortable-url'); + data = {}; + component_prefix = row.closest('.datagrid').find('tbody').attr('data-sortable-parent-path'); + data[(component_prefix + '-item_id').replace(/^-/, '')] = item_id; + if (prev_id !== null) { + data[(component_prefix + '-prev_id').replace(/^-/, '')] = prev_id; + } + if (next_id !== null) { + data[(component_prefix + '-next_id').replace(/^-/, '')] = next_id; + } + return dataGridRegisterAjaxCall({ + type: 'GET', + url: url, + data: data, + error: function(jqXHR, textStatus, errorThrown) { + return alert(jqXHR.statusText); + } + }); + }, + helper: function(e, ui) { + ui.children().each(function() { + return $(this).width($(this).width()); + }); + return ui; + } + }); +}; + +$(function() { + return datagridSortable(); +}); + +if (typeof datagridSortableTree === 'undefined') { + datagridSortableTree = function() { + if (typeof $('.datagrid-tree-item-children').sortable === 'undefined') { + return; + } + return $('.datagrid-tree-item-children').sortable({ + handle: '.handle-sort', + items: '.datagrid-tree-item:not(.datagrid-tree-header)', + toleranceElement: '> .datagrid-tree-item-content', + connectWith: '.datagrid-tree-item-children', + update: function(event, ui) { + var component_prefix, data, item_id, next_id, parent, parent_id, prev_id, row, url; + $('.toggle-tree-to-delete').remove(); + row = ui.item.closest('.datagrid-tree-item[data-id]'); + item_id = row.data('id'); + prev_id = null; + next_id = null; + parent_id = null; + if (row.prev().length) { + prev_id = row.prev().data('id'); + } + if (row.next().length) { + next_id = row.next().data('id'); + } + parent = row.parent().closest('.datagrid-tree-item'); + if (parent.length) { + parent.find('.datagrid-tree-item-children').first().css({ + display: 'block' + }); + parent.addClass('has-children'); + parent_id = parent.data('id'); + } + url = $(this).data('sortable-url'); + if (!url) { + return; + } + parent.find('[data-toggle-tree]').first().removeClass('hidden'); + component_prefix = row.closest('.datagrid-tree').attr('data-sortable-parent-path'); + data = {}; + data[(component_prefix + '-item_id').replace(/^-/, '')] = item_id; + if (prev_id !== null) { + data[(component_prefix + '-prev_id').replace(/^-/, '')] = prev_id; + } + if (next_id !== null) { + data[(component_prefix + '-next_id').replace(/^-/, '')] = next_id; + } + data[(component_prefix + '-parent_id').replace(/^-/, '')] = parent_id; + return dataGridRegisterAjaxCall({ + type: 'GET', + url: url, + data: data, + error: function(jqXHR, textStatus, errorThrown) { + if (errorThrown !== 'abort') { + return alert(jqXHR.statusText); + } + } + }); + }, + stop: function(event, ui) { + return $('.toggle-tree-to-delete').removeClass('toggle-tree-to-delete'); + }, + start: function(event, ui) { + var parent; + parent = ui.item.parent().closest('.datagrid-tree-item'); + if (parent.length) { + if (parent.find('.datagrid-tree-item').length === 2) { + return parent.find('[data-toggle-tree]').addClass('toggle-tree-to-delete'); + } + } + } + }); + }; +} + +$(function() { + return datagridSortableTree(); +}); + +dataGridRegisterExtension('datagrid.happy', { + success: function() { + var c, checked_rows, class_selector, classes, event, grid, grids, i, ie, input, j, len, len1, results; + if (window.happy) { + window.happy.reset(); + } + grids = $('.datagrid'); + results = []; + for (i = 0, len = grids.length; i < len; i++) { + grid = grids[i]; + classes = grid.classList; + class_selector = ''; + for (j = 0, len1 = classes.length; j < len1; j++) { + c = classes[j]; + class_selector = class_selector + '.' + c; + } + checked_rows = document.querySelectorAll(class_selector + ' ' + 'input[data-check]:checked'); + if (checked_rows.length === 1 && checked_rows[0].getAttribute('name') === 'toggle-all') { + input = document.querySelector(class_selector + ' input[name=toggle-all]'); + if (input) { + input.checked = false; + ie = window.navigator.userAgent.indexOf("MSIE "); + if (ie) { + event = document.createEvent('Event'); + event.initEvent('change', true, true); + } else { + event = new Event('change', { + 'bubbles': true + }); + } + results.push(input.dispatchEvent(event)); + } else { + results.push(void 0); + } + } else { + results.push(void 0); + } + } + return results; + } +}); + +dataGridRegisterExtension('datagrid.sortable', { + success: function() { + return datagridSortable(); + } +}); + +dataGridRegisterExtension('datagrid.forms', { + success: function() { + return $('.datagrid').find('form').each(function() { + return window.Nette.initForm(this); + }); + } +}); + +dataGridRegisterExtension('datagrid.url', { + success: function(payload) { + var host, path, query, url; + if (payload._datagrid_url) { + if (window.history.replaceState) { + host = window.location.protocol + "//" + window.location.host; + path = window.location.pathname; + query = window.datagridSerializeUrl(payload.state).replace(/&+$/gm, ''); + if (query) { + url = host + path + "?" + query.replace(/\&*$/, ''); + } else { + url = host + path; + } + url += window.location.hash; + if (window.location.href !== url) { + return window.history.replaceState({ + path: url + }, '', url); + } + } + } + } +}); + +dataGridRegisterExtension('datagrid.sort', { + success: function(payload) { + var href, key, ref, results; + if (payload._datagrid_sort) { + ref = payload._datagrid_sort; + results = []; + for (key in ref) { + href = ref[key]; + results.push($('#datagrid-sort-' + key).attr('href', href)); + } + return results; + } + } +}); + +dataGridRegisterExtension('datargid.item_detail', { + before: function(xhr, settings) { + var id, row_detail, grid_fullname; + if (settings.nette && settings.nette.el.attr('data-toggle-detail')) { + id = settings.nette.el.attr('data-toggle-detail'); + grid_fullname = settings.nette.el.attr('data-toggle-detail-grid-fullname'); + row_detail = $('.item-detail-' + grid_fullname + '-id-' + id); + if (row_detail.hasClass('loaded')) { + if (!row_detail.find('.item-detail-content').length) { + row_detail.removeClass('toggled'); + return true; + } + if (row_detail.hasClass('toggled')) { + row_detail.find('.item-detail-content').slideToggle('fast', (function(_this) { + return function() { + return row_detail.toggleClass('toggled'); + }; + })(this)); + } else { + row_detail.toggleClass('toggled'); + row_detail.find('.item-detail-content').slideToggle('fast'); + } + return false; + } else { + return row_detail.addClass('loaded'); + } + } + return true; + }, + success: function(payload) { + var id, row_detail, grid_fullname; + if (payload._datagrid_toggle_detail && payload._datagrid_name) { + id = payload._datagrid_toggle_detail; + grid_fullname = payload._datagrid_name; + row_detail = $('.item-detail-' + grid_fullname + '-id-' + id); + row_detail.toggleClass('toggled'); + return row_detail.find('.item-detail-content').slideToggle('fast'); + } + } +}); + +dataGridRegisterExtension('datagrid.tree', { + before: function(xhr, settings) { + var children_block; + if (settings.nette && settings.nette.el.attr('data-toggle-tree')) { + settings.nette.el.toggleClass('toggle-rotate'); + children_block = settings.nette.el.closest('.datagrid-tree-item').find('.datagrid-tree-item-children').first(); + if (children_block.hasClass('loaded')) { + children_block.slideToggle('fast'); + return false; + } + } + return true; + }, + success: function(payload) { + var children_block, content, id, name, ref, snippet, template; + if (payload._datagrid_tree) { + id = payload._datagrid_tree; + children_block = $('.datagrid-tree-item[data-id="' + id + '"]').find('.datagrid-tree-item-children').first(); + children_block.addClass('loaded'); + ref = payload.snippets; + for (name in ref) { + snippet = ref[name]; + content = $(snippet); + template = $('
'); + template.attr('data-id', content.attr('data-id')); + template.append(content); + if (content.data('has-children')) { + template.addClass('has-children'); + } + children_block.append(template); + } + children_block.addClass('loaded'); + children_block.slideToggle('fast'); + dataGridLoad(); + } + return datagridSortableTree(); + } +}); + +$(document).on('click', '[data-datagrid-editable-url]', function(event) { + var attr_name, attr_value, attrs, cell, cellValue, cell_height, cell_lines, cell_padding, input, line_height, submit, valueToEdit; + cell = $(this); + if (event.target.tagName.toLowerCase() === 'a') { + return; + } + if (cell.hasClass('datagrid-inline-edit')) { + return; + } + if (!cell.hasClass('editing')) { + cell.addClass('editing'); + cellValue = cell.html().trim().replace('
', '\n'); + if (cell.attr('data-datagrid-editable-value')) { + valueToEdit = String(cell.data('datagrid-editable-value')); + } else { + valueToEdit = cellValue; + } + cell.data('originalValue', cellValue); + cell.data('valueToEdit', valueToEdit); + if (cell.data('datagrid-editable-type') === 'textarea') { + input = $(''); + cell_padding = parseInt(cell.css('padding').replace(/[^-\d\.]/g, ''), 10); + cell_height = cell.outerHeight(); + line_height = Math.round(parseFloat(cell.css('line-height'))); + cell_lines = (cell_height - (2 * cell_padding)) / line_height; + input.attr('rows', Math.round(cell_lines)); + } else if (cell.data('datagrid-editable-type') === 'select') { + input = $(cell.data('datagrid-editable-element')); + input.find("option[value='" + valueToEdit + "']").prop('selected', true); + } else { + input = $(''); + input.val(valueToEdit); + } + attrs = cell.data('datagrid-editable-attrs'); + for (attr_name in attrs) { + attr_value = attrs[attr_name]; + input.attr(attr_name, attr_value); + } + cell.removeClass('edited'); + cell.html(input); + submit = function(cell, el) { + var value; + value = el.val(); + if (value !== cell.data('valueToEdit')) { + dataGridRegisterAjaxCall({ + url: cell.data('datagrid-editable-url'), + data: { + value: value + }, + type: 'POST', + success: function(payload) { + if (cell.data('datagrid-editable-type') === 'select') { + cell.html(input.find("option[value='" + value + "']").html()); + } else { + if (payload._datagrid_editable_new_value) { + value = payload._datagrid_editable_new_value; + } + cell.html(value); + } + return cell.addClass('edited'); + }, + error: function() { + cell.html(cell.data('originalValue')); + return cell.addClass('edited-error'); + } + }); + } else { + cell.html(cell.data('originalValue')); + } + return setTimeout(function() { + return cell.removeClass('editing'); + }, 1200); + }; + cell.find('input,textarea,select').focus().on('blur', function() { + return submit(cell, $(this)); + }).on('keydown', function(e) { + if (cell.data('datagrid-editable-type') !== 'textarea') { + if (e.which === 13) { + e.stopPropagation(); + e.preventDefault(); + return submit(cell, $(this)); + } + } + if (e.which === 27) { + e.stopPropagation(); + e.preventDefault(); + cell.removeClass('editing'); + return cell.html(cell.data('originalValue')); + } + }); + return cell.find('select').on('change', function() { + return submit(cell, $(this)); + }); + } +}); + +dataGridRegisterExtension('datagrid.after_inline_edit', { + success: function(payload) { + var grid = $('.datagrid-' + payload._datagrid_name); + + if (payload._datagrid_inline_edited) { + grid.find('tr[data-id="' + payload._datagrid_inline_edited + '"] > td').addClass('edited'); + return grid.find('.datagrid-inline-edit-trigger').removeClass('hidden'); + } else if (payload._datagrid_inline_edit_cancel) { + return grid.find('.datagrid-inline-edit-trigger').removeClass('hidden'); + } + } +}); + +$(document).on('mouseup', '[data-datagrid-cancel-inline-add]', function(e) { + var code = e.which || e.keyCode || 0; + if (code === 1) { + e.stopPropagation(); + e.preventDefault(); + return $('.datagrid-row-inline-add').addClass('datagrid-row-inline-add-hidden'); + } +}); + +dataGridRegisterExtension('datagrid-toggle-inline-add', { + success: function(payload) { + var grid = $('.datagrid-' + payload._datagrid_name); + + if (payload._datagrid_inline_adding) { + var row = grid.find('.datagrid-row-inline-add'); + + if (row.hasClass('datagrid-row-inline-add-hidden')) { + row.removeClass('datagrid-row-inline-add-hidden'); + } + + row.find('input:not([readonly]),textarea:not([readonly])').first().focus(); + } + } +}); + +datagridFilterMultiSelect = function() { + var select = $('.selectpicker').first(); + + if ($.fn.selectpicker) { + let defaults = $.fn.selectpicker.defaults = { + countSelectedText: select.data('i18n-selected'), + iconBase: '', + tickIcon: select.data('selected-icon-check') + }; + + $('.selectpicker') + .removeClass('form-select form-select-sm') + .addClass('form-control form-control-sm') + .selectpicker('destroy') + .selectpicker({ + iconBase: 'fa' + }); + + return defaults; + } +}; + +$(function() { + return datagridFilterMultiSelect(); +}); + +datagridGroupActionMultiSelect = function() { + var selects; + + if (!$.fn.selectpicker) { + return; + } + + selects = $('[data-datagrid-multiselect-id]'); + + return selects.each(function() { + var id; + if ($(this).hasClass('selectpicker')) { + $(this).removeAttr('id'); + id = $(this).data('datagrid-multiselect-id'); + $(this).on('loaded.bs.select', function(e) { + $(this).parent().attr('style', 'display:none;'); + return $(this).parent().find('.hidden').removeClass('hidden').addClass('btn-default btn-secondary'); + }); + return $(this).on('rendered.bs.select', function(e) { + return $(this).parent().attr('id', id); + }); + } + }); +}; + +$(function() { + return datagridGroupActionMultiSelect(); +}); + +dataGridRegisterExtension('datagrid.fitlerMultiSelect', { + success: function() { + datagridFilterMultiSelect(); + } +}); + +dataGridRegisterExtension('datagrid.groupActionMultiSelect', { + success: function() { + return datagridGroupActionMultiSelect(); + } +}); + +dataGridRegisterExtension('datagrid.inline-editing', { + success: function(payload) { + var grid; + if (payload._datagrid_inline_editing) { + grid = $('.datagrid-' + payload._datagrid_name); + return grid.find('.datagrid-inline-edit-trigger').addClass('hidden'); + } + } +}); + +dataGridRegisterExtension('datagrid.redraw-item', { + success: function(payload) { + var row; + if (payload._datagrid_redraw_item_class) { + row = $('tr[data-id="' + payload._datagrid_redraw_item_id + '"]'); + return row.attr('class', payload._datagrid_redraw_item_class); + } + } +}); + +dataGridRegisterExtension('datagrid.reset-filter-by-column', { + success: function(payload) { + var grid, href, i, key, len, ref; + if (!payload._datagrid_name) { + return; + } + grid = $('.datagrid-' + payload._datagrid_name); + grid.find('[data-datagrid-reset-filter-by-column]').addClass('hidden'); + if (payload.non_empty_filters && payload.non_empty_filters.length) { + ref = payload.non_empty_filters; + for (i = 0, len = ref.length; i < len; i++) { + key = ref[i]; + grid.find('[data-datagrid-reset-filter-by-column="' + key + '"]').removeClass('hidden'); + } + href = grid.find('.reset-filter').attr('href'); + return grid.find('[data-datagrid-reset-filter-by-column]').each(function() { + var new_href; + key = $(this).attr('data-datagrid-reset-filter-by-column'); + new_href = href.replace('do=' + payload._datagrid_name + '-resetFilter', 'do=' + payload._datagrid_name + '-resetColumnFilter'); + new_href += '&' + payload._datagrid_name + '-key=' + key; + return $(this).attr('href', new_href); + }); + } + } +}); diff --git a/assets/js/datagrid/instant-url-refresh.js b/assets/js/datagrid/instant-url-refresh.js new file mode 100644 index 0000000..d0caef0 --- /dev/null +++ b/assets/js/datagrid/instant-url-refresh.js @@ -0,0 +1,30 @@ +var dataGridRegisterAjaxCall; + +if (typeof naja !== "undefined") { + dataGridRegisterAjaxCall = function (params) { + var method = params.type || 'GET'; + var data = params.data || null; + + naja.makeRequest(method, params.url, data, { + history: 'replace' + }) + .then(params.success) + .catch(params.error); + }; + +} else { + dataGridRegisterAjaxCall = function (params) { + $.nette.ajax(params); + }; +} + +document.addEventListener('DOMContentLoaded', function () { + var element = document.querySelector('.datagrid'); + + if (element !== null) { + return dataGridRegisterAjaxCall({ + type: 'GET', + url: element.getAttribute('data-refresh-state') + }); + } +}); diff --git a/assets/js/datagrid/spinners.js b/assets/js/datagrid/spinners.js new file mode 100644 index 0000000..a680ba3 --- /dev/null +++ b/assets/js/datagrid/spinners.js @@ -0,0 +1,89 @@ +var dataGridRegisterExtension; + +if (typeof naja !== "undefined") { + var isNaja2 = function () { return naja && naja.VERSION && naja.VERSION >= 2 }; + var najaEventParams = function (params) { return isNaja2() ? params.detail : params }; + var najaRequest = function (params) { return isNaja2() ? params.detail.request : params.xhr }; + dataGridRegisterExtension = function (name, extension) { + var init = extension.init; + var success = extension.success; + var before = extension.before; + var complete = extension.complete; + + + var NewExtension = function NewExtension(naja, name) { + this.name = name; + + this.initialize = function (naja) { + if(init) { + naja.addEventListener('init', function (params) { + init(najaEventParams(params).defaultOptions); + }); + } + + if(success) { + naja.addEventListener('success', function (params) { + var payload = isNaja2() ? params.detail.payload : params.response; + success(payload, najaEventParams(params).options); + }); + } + + if(before) { + naja.addEventListener('before', function (params) { + before(najaRequest(params), najaEventParams(params).options); + }); + } + + if(complete) { + naja.addEventListener('complete', function (params) { + complete(najaRequest(params), najaEventParams(params).options); + }); + } + } + if (!isNaja2()) { + this.initialize(naja); + } + return this; + } + + if (isNaja2()) { + naja.registerExtension(new NewExtension(null, name)); + } else { + naja.registerExtension(NewExtension, name); + } + }; +} else if ($.nette) { + dataGridRegisterExtension = function (name, extension) { + $.nette.ext(name, extension); + }; +} + +dataGridRegisterExtension('ublaboo-spinners', { + before: function(xhr, settings) { + var el, id, row_detail, spinner_template, grid_fullname; + if (settings.nette) { + el = settings.nette.el; + spinner_template = $('
'); + if (el.is('.datagrid [name="group_action[submit]"]')) { + return el.after(spinner_template); + } else if (el.is('.datagrid a') && el.data('toggle-detail')) { + id = settings.nette.el.attr('data-toggle-detail'); + grid_fullname = settings.nette.el.attr('data-toggle-detail-grid-fullname'); + row_detail = $('.item-detail-' + grid_fullname + '-id-' + id); + if (!row_detail.hasClass('loaded')) { + return el.addClass('ublaboo-spinner-icon'); + } + } else if (el.is('.datagrid .col-pagination a')) { + return el.closest('.row-grid-bottom').find('.col-per-page').prepend(spinner_template); + } else if (el.is('.datagrid .datagrid-per-page-submit')) { + return el.closest('.row-grid-bottom').find('.col-per-page').prepend(spinner_template); + } else if (el.is('.datagrid .reset-filter')) { + return el.closest('.row-grid-bottom').find('.col-per-page').prepend(spinner_template); + } + } + }, + complete: function() { + $('.ublaboo-spinner').remove(); + return $('.ublaboo-spinner-icon').removeClass('ublaboo-spinner-icon'); + } +}); diff --git a/assets/js/main.js b/assets/js/main.js new file mode 100644 index 0000000..be1ed92 --- /dev/null +++ b/assets/js/main.js @@ -0,0 +1,26 @@ +// import 'ublaboo-datagrid/assets/datagrid.js'; +// import 'ublaboo-datagrid/assets/datagrid-spinners.js'; +// import 'ublaboo-datagrid/assets/datagrid-instant-url-refresh.js'; +import naja from "naja"; +import netteForms from "nette-forms"; +// Code highlighting +import Prism from "prismjs/components/prism-core"; +import "prismjs/components/prism-markup-templating"; +import "prismjs/components/prism-php"; +import "prismjs/components/prism-clike"; +import "prismjs/components/prism-javascript"; +import "prismjs/components/prism-css"; +// Styles +import '../css/main.css'; + +document.addEventListener("DOMContentLoaded", () => { + // AJAX + naja.formsHandler.netteForms = netteForms; + naja.initialize(); + + // Highlighting + const codes = document.querySelectorAll('code'); + codes.forEach(code => { + Prism.highlightElement(code); + }); +}); diff --git a/www/favicon.ico b/assets/public/favicon.ico similarity index 100% rename from www/favicon.ico rename to assets/public/favicon.ico diff --git a/www/assets/prism.css b/www/assets/prism.css deleted file mode 100644 index 43af91f..0000000 --- a/www/assets/prism.css +++ /dev/null @@ -1,126 +0,0 @@ -/* PrismJS 1.20.0 -https://prismjs.com/download.html#themes=prism-okaidia&languages=markup+clike+javadoclike+markup-templating+php+phpdoc+php-extras */ -/** - * okaidia theme for JavaScript, CSS and HTML - * Loosely based on Monokai textmate theme by http://www.monokai.nl/ - * @author ocodia - */ - -code[class*="language-"], -pre[class*="language-"] { - color: #f8f8f2; - background: none; - text-shadow: 0 1px rgba(0, 0, 0, 0.3); - font-family: Consolas, Monaco, 'Andale Mono', 'Ubuntu Mono', monospace; - font-size: 1em; - text-align: left; - white-space: pre; - word-spacing: normal; - word-break: normal; - word-wrap: normal; - line-height: 1.5; - - -moz-tab-size: 4; - -o-tab-size: 4; - tab-size: 4; - - -webkit-hyphens: none; - -moz-hyphens: none; - -ms-hyphens: none; - hyphens: none; -} - -/* Code blocks */ -pre[class*="language-"] { - padding: 1em; - margin: .5em 0; - overflow: auto; - border-radius: 0.3em; -} - -:not(pre) > code[class*="language-"], -pre[class*="language-"] { - background: #272822; -} - -/* Inline code */ -:not(pre) > code[class*="language-"] { - padding: .1em; - border-radius: .3em; - white-space: normal; -} - -.token.comment, -.token.prolog, -.token.doctype, -.token.cdata { - color: slategray; -} - -.token.punctuation { - color: #f8f8f2; -} - -.token.namespace { - opacity: .7; -} - -.token.property, -.token.tag, -.token.constant, -.token.symbol, -.token.deleted { - color: #f92672; -} - -.token.boolean, -.token.number { - color: #ae81ff; -} - -.token.selector, -.token.attr-name, -.token.string, -.token.char, -.token.builtin, -.token.inserted { - color: #a6e22e; -} - -.token.operator, -.token.entity, -.token.url, -.language-css .token.string, -.style .token.string, -.token.variable { - color: #f8f8f2; -} - -.token.atrule, -.token.attr-value, -.token.function, -.token.class-name { - color: #e6db74; -} - -.token.keyword { - color: #66d9ef; -} - -.token.regex, -.token.important { - color: #fd971f; -} - -.token.important, -.token.bold { - font-weight: bold; -} -.token.italic { - font-style: italic; -} - -.token.entity { - cursor: help; -} - diff --git a/www/assets/prism.js b/www/assets/prism.js deleted file mode 100644 index 246380d..0000000 --- a/www/assets/prism.js +++ /dev/null @@ -1,10 +0,0 @@ -/* PrismJS 1.20.0 -https://prismjs.com/download.html#themes=prism-okaidia&languages=markup+clike+javadoclike+markup-templating+php+phpdoc+php-extras */ -var _self="undefined"!=typeof window?window:"undefined"!=typeof WorkerGlobalScope&&self instanceof WorkerGlobalScope?self:{},Prism=function(u){var c=/\blang(?:uage)?-([\w-]+)\b/i,n=0,C={manual:u.Prism&&u.Prism.manual,disableWorkerMessageHandler:u.Prism&&u.Prism.disableWorkerMessageHandler,util:{encode:function e(n){return n instanceof _?new _(n.type,e(n.content),n.alias):Array.isArray(n)?n.map(e):n.replace(/&/g,"&").replace(/n.length)return;if(!(b instanceof _)){var x=1;if(d&&y!=t.tail.prev){g.lastIndex=k;var w=g.exec(n);if(!w)break;var A=w.index+(h&&w[1]?w[1].length:0),P=w.index+w[0].length,S=k;for(S+=y.value.length;S<=A;)y=y.next,S+=y.value.length;if(S-=y.value.length,k=S,y.value instanceof _)continue;for(var O=y;O!==t.tail&&(S"+a.content+""},!u.document)return u.addEventListener&&(C.disableWorkerMessageHandler||u.addEventListener("message",function(e){var n=JSON.parse(e.data),t=n.language,r=n.code,a=n.immediateClose;u.postMessage(C.highlight(r,C.languages[t],t)),a&&u.close()},!1)),C;var e=C.util.currentScript();function t(){C.manual||C.highlightAll()}if(e&&(C.filename=e.src,e.hasAttribute("data-manual")&&(C.manual=!0)),!C.manual){var r=document.readyState;"loading"===r||"interactive"===r&&e&&e.defer?document.addEventListener("DOMContentLoaded",t):window.requestAnimationFrame?window.requestAnimationFrame(t):window.setTimeout(t,16)}return C}(_self);"undefined"!=typeof module&&module.exports&&(module.exports=Prism),"undefined"!=typeof global&&(global.Prism=Prism); -Prism.languages.markup={comment://,prolog:/<\?[\s\S]+?\?>/,doctype:{pattern:/"'[\]]|"[^"]*"|'[^']*')+(?:\[(?:[^<"'\]]|"[^"]*"|'[^']*'|<(?!!--)|)*\]\s*)?>/i,greedy:!0},cdata://i,tag:{pattern:/<\/?(?!\d)[^\s>\/=$<%]+(?:\s(?:\s*[^\s>\/=]+(?:\s*=\s*(?:"[^"]*"|'[^']*'|[^\s'">=]+(?=[\s>]))|(?=[\s/>])))+)?\s*\/?>/i,greedy:!0,inside:{tag:{pattern:/^<\/?[^\s>\/]+/i,inside:{punctuation:/^<\/?/,namespace:/^[^\s>\/:]+:/}},"attr-value":{pattern:/=\s*(?:"[^"]*"|'[^']*'|[^\s'">=]+)/i,inside:{punctuation:[/^=/,{pattern:/^(\s*)["']|["']$/,lookbehind:!0}]}},punctuation:/\/?>/,"attr-name":{pattern:/[^\s>\/]+/,inside:{namespace:/^[^\s>\/:]+:/}}}},entity:/&#?[\da-z]{1,8};/i},Prism.languages.markup.tag.inside["attr-value"].inside.entity=Prism.languages.markup.entity,Prism.hooks.add("wrap",function(a){"entity"===a.type&&(a.attributes.title=a.content.replace(/&/,"&"))}),Object.defineProperty(Prism.languages.markup.tag,"addInlined",{value:function(a,e){var s={};s["language-"+e]={pattern:/(^$)/i,lookbehind:!0,inside:Prism.languages[e]},s.cdata=/^$/i;var n={"included-cdata":{pattern://i,inside:s}};n["language-"+e]={pattern:/[\s\S]+/,inside:Prism.languages[e]};var t={};t[a]={pattern:RegExp("(<__[^]*?>)(?:))*\\]\\]>|(?!)".replace(/__/g,function(){return a}),"i"),lookbehind:!0,greedy:!0,inside:n},Prism.languages.insertBefore("markup","cdata",t)}}),Prism.languages.xml=Prism.languages.extend("markup",{}),Prism.languages.html=Prism.languages.markup,Prism.languages.mathml=Prism.languages.markup,Prism.languages.svg=Prism.languages.markup; -Prism.languages.clike={comment:[{pattern:/(^|[^\\])\/\*[\s\S]*?(?:\*\/|$)/,lookbehind:!0},{pattern:/(^|[^\\:])\/\/.*/,lookbehind:!0,greedy:!0}],string:{pattern:/(["'])(?:\\(?:\r\n|[\s\S])|(?!\1)[^\\\r\n])*\1/,greedy:!0},"class-name":{pattern:/(\b(?:class|interface|extends|implements|trait|instanceof|new)\s+|\bcatch\s+\()[\w.\\]+/i,lookbehind:!0,inside:{punctuation:/[.\\]/}},keyword:/\b(?:if|else|while|do|for|return|in|instanceof|function|new|try|throw|catch|finally|null|break|continue)\b/,boolean:/\b(?:true|false)\b/,function:/\w+(?=\()/,number:/\b0x[\da-f]+\b|(?:\b\d+\.?\d*|\B\.\d+)(?:e[+-]?\d+)?/i,operator:/[<>]=?|[!=]=?=?|--?|\+\+?|&&?|\|\|?|[?*/~^%]/,punctuation:/[{}[\];(),.:]/}; -!function(h){function v(e,n){return"___"+e.toUpperCase()+n+"___"}Object.defineProperties(h.languages["markup-templating"]={},{buildPlaceholders:{value:function(a,r,e,o){if(a.language===r){var c=a.tokenStack=[];a.code=a.code.replace(e,function(e){if("function"==typeof o&&!o(e))return e;for(var n,t=c.length;-1!==a.code.indexOf(n=v(r,t));)++t;return c[t]=e,n}),a.grammar=h.languages.markup}}},tokenizePlaceholders:{value:function(p,k){if(p.language===k&&p.tokenStack){p.grammar=h.languages[k];var m=0,d=Object.keys(p.tokenStack);!function e(n){for(var t=0;t=d.length);t++){var a=n[t];if("string"==typeof a||a.content&&"string"==typeof a.content){var r=d[m],o=p.tokenStack[r],c="string"==typeof a?a:a.content,i=v(k,r),u=c.indexOf(i);if(-1$|^<\?(?:php(?=\s)|=)?/i,alias:"important"}}),n.languages.insertBefore("php","keyword",{variable:/\$+(?:\w+\b|(?={))/i,package:{pattern:/(\\|namespace\s+|use\s+)[\w\\]+/,lookbehind:!0,inside:{punctuation:/\\/}}}),n.languages.insertBefore("php","operator",{property:{pattern:/(->)[\w]+/,lookbehind:!0}});var e={pattern:/{\$(?:{(?:{[^{}]+}|[^{}]+)}|[^{}])+}|(^|[^\\{])\$+(?:\w+(?:\[[^\r\n\[\]]+\]|->\w+)*)/,lookbehind:!0,inside:n.languages.php};n.languages.insertBefore("php","string",{"nowdoc-string":{pattern:/<<<'([^']+)'[\r\n](?:.*[\r\n])*?\1;/,greedy:!0,alias:"string",inside:{delimiter:{pattern:/^<<<'[^']+'|[a-z_]\w*;$/i,alias:"symbol",inside:{punctuation:/^<<<'?|[';]$/}}}},"heredoc-string":{pattern:/<<<(?:"([^"]+)"[\r\n](?:.*[\r\n])*?\1;|([a-z_]\w*)[\r\n](?:.*[\r\n])*?\2;)/i,greedy:!0,alias:"string",inside:{delimiter:{pattern:/^<<<(?:"[^"]+"|[a-z_]\w*)|[a-z_]\w*;$/i,alias:"symbol",inside:{punctuation:/^<<<"?|[";]$/}},interpolation:e}},"single-quoted-string":{pattern:/'(?:\\[\s\S]|[^\\'])*'/,greedy:!0,alias:"string"},"double-quoted-string":{pattern:/"(?:\\[\s\S]|[^\\"])*"/,greedy:!0,alias:"string",inside:{interpolation:e}}}),delete n.languages.php.string,n.hooks.add("before-tokenize",function(e){if(/<\?/.test(e.code)){n.languages["markup-templating"].buildPlaceholders(e,"php",/<\?(?:[^"'/#]|\/(?![*/])|("|')(?:\\[\s\S]|(?!\1)[^\\])*\1|(?:\/\/|#)(?:[^?\n\r]|\?(?!>))*(?=$|\?>|[\r\n])|\/\*[\s\S]*?(?:\*\/|$))*?(?:\?>|$)/gi)}}),n.hooks.add("after-tokenize",function(e){n.languages["markup-templating"].tokenizePlaceholders(e,"php")})}(Prism); -!function(p){var a=p.languages.javadoclike={parameter:{pattern:/(^\s*(?:\/{3}|\*|\/\*\*)\s*@(?:param|arg|arguments)\s+)\w+/m,lookbehind:!0},keyword:{pattern:/(^\s*(?:\/{3}|\*|\/\*\*)\s*|\{)@[a-z][a-zA-Z-]+\b/m,lookbehind:!0},punctuation:/[{}]/};Object.defineProperty(a,"addSupport",{value:function(a,e){"string"==typeof a&&(a=[a]),a.forEach(function(a){!function(a,e){var n="doc-comment",t=p.languages[a];if(t){var r=t[n];if(!r){var o={"doc-comment":{pattern:/(^|[^\\])\/\*\*[^/][\s\S]*?(?:\*\/|$)/,lookbehind:!0,alias:"comment"}};r=(t=p.languages.insertBefore(a,"comment",o))[n]}if(r instanceof RegExp&&(r=t[n]={pattern:r}),Array.isArray(r))for(var i=0,s=r.length;i 0) { - setTimeout( - function() { - $('.flash').remove(); - }, - 4000 - ); - } -}; - -if (typeof naja !== "undefined") { - function FlashesExtension(naja) { - naja.addEventListener('complete', finishFlash); - - return this; - } - - naja.registerExtension(FlashesExtension); -} else { - $.nette.ext('flashes', { - complete: function() { - finishFlash(); - } - }); -} - -finishFlash(); diff --git a/www/index.php b/www/index.php index 9e5ffde..0996575 100644 --- a/www/index.php +++ b/www/index.php @@ -1,13 +1,5 @@ -createContainer() - ->getByType(Application::class) - ->run(); +App\Bootstrap::run(); diff --git a/www/package-lock.json b/www/package-lock.json deleted file mode 100644 index a4d8f93..0000000 --- a/www/package-lock.json +++ /dev/null @@ -1,60 +0,0 @@ -{ - "requires": true, - "lockfileVersion": 1, - "dependencies": { - "bootstrap": { - "version": "4.4.1", - "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-4.4.1.tgz", - "integrity": "sha512-tbx5cHubwE6e2ZG7nqM3g/FZ5PQEDMWmMGNrCUBVRPHXTJaH7CBDdsLeu3eCh3B1tzAxTnAbtmrzvWEvT2NNEA==", - "dev": true - }, - "bootstrap-datepicker": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/bootstrap-datepicker/-/bootstrap-datepicker-1.9.0.tgz", - "integrity": "sha512-9rYYbaVOheGYxjOr/+bJCmRPihfy+LkLSg4fIFMT9Od8WwWB/MB50w0JO1eBgKUMbb7PFHQD5uAfI3ArAxZRXA==", - "requires": { - "jquery": ">=1.7.1 <4.0.0" - } - }, - "bootstrap-select": { - "version": "1.13.14", - "resolved": "https://registry.npmjs.org/bootstrap-select/-/bootstrap-select-1.13.14.tgz", - "integrity": "sha512-TiL2BobDTwPNV1pteDhukepamPXnbH33+B7D9oMI672KnsyDl0/j6lfQ+0TCL74TI1vaUv+gjL/0nvpmiTCzxQ==" - }, - "happy-inputs": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/happy-inputs/-/happy-inputs-2.0.4.tgz", - "integrity": "sha512-3ddO912xhms26FcNqpYJuV09lKsj+h0x7se9cWnTNvNjOmsoeQ7yrfKhNJiLwfmLmhF+Ut4dH8s09TABNsL6Hg==" - }, - "jquery": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.5.0.tgz", - "integrity": "sha512-Xb7SVYMvygPxbFMpTFQiHh1J7HClEaThguL15N/Gg37Lri/qKyhRGZYzHRyLH8Stq3Aow0LsHO2O2ci86fCrNQ==" - }, - "jquery-ui-sortable": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/jquery-ui-sortable/-/jquery-ui-sortable-1.0.0.tgz", - "integrity": "sha1-DuBizgKymzZYXt46Pg3d5mYGD5Y=" - }, - "nette-forms": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/nette-forms/-/nette-forms-3.0.4.tgz", - "integrity": "sha512-Z9Ia5T38mXQ81gMku/h9O2v+ZzFt5RgdI4lXaCNWH/HxJZAsViQUyDoYTLMNhwYJ7vx6Yzl1HusmlMHoTIZG3w==" - }, - "nette.ajax.js": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/nette.ajax.js/-/nette.ajax.js-2.3.0.tgz", - "integrity": "sha1-QmdSyyoAmIVw7XCqK9xY0HLMA1Q=" - }, - "popper.js": { - "version": "1.16.1", - "resolved": "https://registry.npmjs.org/popper.js/-/popper.js-1.16.1.tgz", - "integrity": "sha512-Wb4p1J4zyFTbM+u6WuO4XstYx4Ky9Cewe4DWrel7B0w6VVICvPwdOpotjzcf6eD8TsckVnIMNONQyPIUFOUbCQ==" - }, - "ublaboo-datagrid": { - "version": "6.2.13", - "resolved": "https://registry.npmjs.org/ublaboo-datagrid/-/ublaboo-datagrid-6.2.13.tgz", - "integrity": "sha512-AbnhulHMUiyhxPx1XtbUt1WRX2llKTqUDH4WxSyYCfvPbRehzkOa3ygb64+ZIYS4YSKaOfHOS3mfCIN5bxajlA==" - } - } -} diff --git a/www/package.json b/www/package.json deleted file mode 100644 index 86fdeba..0000000 --- a/www/package.json +++ /dev/null @@ -1,16 +0,0 @@ -{ - "dependencies": { - "bootstrap-datepicker": "^1.9", - "bootstrap-select": "^1.13", - "happy-inputs": "^2.0", - "jquery-ui-sortable": "^1.0", - "nette-forms": "^3.0", - "nette.ajax.js": "^2.3", - "popper.js": "^1.14.7", - "ublaboo-datagrid": "^6.2.13" - }, - "devDependencies": { - "bootstrap": "^4.4.1", - "jquery": "^3.5.0" - } -} diff --git a/www/phpinfo.php b/www/phpinfo.php deleted file mode 100644 index 61ace19..0000000 --- a/www/phpinfo.php +++ /dev/null @@ -1,2 +0,0 @@ - Date: Wed, 8 Mar 2023 13:31:10 +0100 Subject: [PATCH 28/34] Phpstan: use var/tmp --- phpstan.neon | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/phpstan.neon b/phpstan.neon index 5a9c7c2..24b05e1 100644 --- a/phpstan.neon +++ b/phpstan.neon @@ -9,7 +9,7 @@ parameters: level: 9 phpVersion: 80100 - tmpDir: %currentWorkingDirectory%/temp/phpstan + tmpDir: %currentWorkingDirectory%/var/tmp/phpstan paths: - app From 36f9e1e9569f8730204f2ffea614fda349a2626d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 8 Mar 2023 13:31:16 +0100 Subject: [PATCH 29/34] Readme: sync with current setup --- README.md | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index 46aaf60..68da1a1 100644 --- a/README.md +++ b/README.md @@ -40,21 +40,25 @@ composer create-project -s dev contributte/datagrid-skeleton acme ### Install using [docker](https://github.com/docker/docker/) -1) At first, use GIT to download this project. +1) At first, use Git to download this project. ``` git clone https://github.com/contributte/datagrid-skeleton.git ``` -2) Run command: +2) Setup project. ``` - docker-compose up + make install ``` -3) Open http://localhost and enjoy! +3) Run docker stack. - If you need enter into container (such as `composer update`) run command `docker-compose run web bash`. + ``` + make docker-up + ``` + +4) Open http://localhost and enjoy! ### Composer packages From e61baa26ef295cc082e06ef685944928edf41b22 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mia=20Vali=C5=A1ov=C3=A1=20=28Liliana=29?= <118116415+lilianalillyy@users.noreply.github.com> Date: Tue, 6 Jun 2023 21:20:06 +0200 Subject: [PATCH 30/34] Assets: rewrite to TS and plugins --- app/UI/AbstractPresenter.php | 2 +- assets/css/main.css | 7 +- assets/datagrid/ajax/index.ts | 1 + assets/datagrid/ajax/naja.ts | 135 +++ assets/datagrid/assets/datagrid.css | 632 ++++++++++++ assets/datagrid/assets/happy.css.ts | 464 +++++++++ assets/datagrid/datagrid.ts | 152 +++ assets/datagrid/datagrids.ts | 85 ++ assets/datagrid/index.ts | 6 + .../datagrid/integrations/bootstrap-select.ts | 46 + assets/datagrid/integrations/happy.ts | 222 +++++ assets/datagrid/integrations/index.ts | 5 + assets/datagrid/integrations/sortable-js.ts | 58 ++ assets/datagrid/integrations/tom-select.ts | 23 + .../integrations/vanilla-datepicker.ts | 14 + .../datagrid/plugins/features/autosubmit.ts | 69 ++ .../datagrid/plugins/features/checkboxes.ts | 92 ++ assets/datagrid/plugins/features/confirm.ts | 28 + assets/datagrid/plugins/features/editable.ts | 118 +++ assets/datagrid/plugins/features/inline.ts | 73 ++ .../datagrid/plugins/features/item-detail.ts | 51 + assets/datagrid/plugins/features/treeView.ts | 39 + assets/datagrid/plugins/index.ts | 12 + .../plugins/integrations/datepicker.ts | 17 + assets/datagrid/plugins/integrations/happy.ts | 19 + .../plugins/integrations/nette-forms.ts | 18 + .../plugins/integrations/selectpicker.ts | 17 + .../datagrid/plugins/integrations/sortable.ts | 62 ++ assets/datagrid/types/ajax.d.ts | 136 +++ assets/datagrid/types/datagrid.d.ts | 29 + assets/datagrid/types/index.d.ts | 40 + assets/datagrid/types/integrations.d.ts | 14 + assets/datagrid/utils.ts | 180 ++++ assets/js/datagrid/datagrid.js | 922 ------------------ assets/js/datagrid/instant-url-refresh.js | 30 - assets/js/datagrid/spinners.js | 89 -- assets/js/main.js | 48 +- composer.lock | 223 ++--- config/config.neon | 1 + docker-compose.yml | 4 +- package-lock.json | 189 ++-- package.json | 23 +- tsconfig.json | 32 + var/log/.gitignore | 0 var/tmp/.gitignore | 0 vite.config.js | 1 + 46 files changed, 3190 insertions(+), 1238 deletions(-) create mode 100644 assets/datagrid/ajax/index.ts create mode 100644 assets/datagrid/ajax/naja.ts create mode 100644 assets/datagrid/assets/datagrid.css create mode 100644 assets/datagrid/assets/happy.css.ts create mode 100644 assets/datagrid/datagrid.ts create mode 100644 assets/datagrid/datagrids.ts create mode 100644 assets/datagrid/index.ts create mode 100644 assets/datagrid/integrations/bootstrap-select.ts create mode 100644 assets/datagrid/integrations/happy.ts create mode 100644 assets/datagrid/integrations/index.ts create mode 100644 assets/datagrid/integrations/sortable-js.ts create mode 100644 assets/datagrid/integrations/tom-select.ts create mode 100644 assets/datagrid/integrations/vanilla-datepicker.ts create mode 100644 assets/datagrid/plugins/features/autosubmit.ts create mode 100644 assets/datagrid/plugins/features/checkboxes.ts create mode 100644 assets/datagrid/plugins/features/confirm.ts create mode 100644 assets/datagrid/plugins/features/editable.ts create mode 100644 assets/datagrid/plugins/features/inline.ts create mode 100644 assets/datagrid/plugins/features/item-detail.ts create mode 100644 assets/datagrid/plugins/features/treeView.ts create mode 100644 assets/datagrid/plugins/index.ts create mode 100644 assets/datagrid/plugins/integrations/datepicker.ts create mode 100644 assets/datagrid/plugins/integrations/happy.ts create mode 100644 assets/datagrid/plugins/integrations/nette-forms.ts create mode 100644 assets/datagrid/plugins/integrations/selectpicker.ts create mode 100644 assets/datagrid/plugins/integrations/sortable.ts create mode 100644 assets/datagrid/types/ajax.d.ts create mode 100644 assets/datagrid/types/datagrid.d.ts create mode 100644 assets/datagrid/types/index.d.ts create mode 100644 assets/datagrid/types/integrations.d.ts create mode 100644 assets/datagrid/utils.ts delete mode 100644 assets/js/datagrid/datagrid.js delete mode 100644 assets/js/datagrid/instant-url-refresh.js delete mode 100644 assets/js/datagrid/spinners.js create mode 100644 tsconfig.json mode change 100644 => 100755 var/log/.gitignore mode change 100644 => 100755 var/tmp/.gitignore diff --git a/app/UI/AbstractPresenter.php b/app/UI/AbstractPresenter.php index e5e0204..5b3f3a0 100644 --- a/app/UI/AbstractPresenter.php +++ b/app/UI/AbstractPresenter.php @@ -15,7 +15,7 @@ abstract class AbstractPresenter extends NellaPresenter abstract public function createComponentGrid(): DataGrid; - public function changeStatus(int $id, string $newStatus): void + public function changeStatus($id, string $newStatus): void { if (in_array($newStatus, ['active', 'inactive', 'deleted'], true)) { $data = ['status' => $newStatus]; diff --git a/assets/css/main.css b/assets/css/main.css index cbfe77f..2f39b39 100644 --- a/assets/css/main.css +++ b/assets/css/main.css @@ -1,10 +1,9 @@ @import "@fortawesome/fontawesome-free/css/all.css"; @import 'bootstrap/dist/css/bootstrap.css'; -@import 'bootstrap-datepicker/dist/css/bootstrap-datepicker.css'; -@import 'bootstrap-select/dist/css/bootstrap-select.css'; -@import 'ublaboo-datagrid/assets/datagrid.css'; -@import 'ublaboo-datagrid/assets/datagrid-spinners.css'; @import 'prismjs/themes/prism-okaidia.css'; +@import './../datagrid/assets/datagrid.css'; +@import 'vanillajs-datepicker/css/datepicker-bs5.css'; + /* App styles */ @import './styles.css'; diff --git a/assets/datagrid/ajax/index.ts b/assets/datagrid/ajax/index.ts new file mode 100644 index 0000000..23b37df --- /dev/null +++ b/assets/datagrid/ajax/index.ts @@ -0,0 +1 @@ +export * from "./naja"; diff --git a/assets/datagrid/ajax/naja.ts b/assets/datagrid/ajax/naja.ts new file mode 100644 index 0000000..b9d0840 --- /dev/null +++ b/assets/datagrid/ajax/naja.ts @@ -0,0 +1,135 @@ +import type {Naja} from "naja"; +import type { + Ajax, + RequestParams, + Payload, + DatagridPayload, + EventDetail, + EventListener, + Response as AjaxResponse, + BaseRequestParams as AjaxBaseRequestParams, + BeforeEventDetail as BaseBeforeEventDetail, + ErrorEventDetail as BaseErrorEventDetail, + InteractEventDetail as BaseInteractEventDetail, + SuccessEventDetail as BaseSuccessEventDetail, + AjaxEventMap as BaseAjaxEventMap, +} from "@datagrid/types"; +import {Datagrid} from "@datagrid/datagrid"; +import {BeforeEvent, SuccessEvent, ErrorEvent, Payload as NajaPayload} from "naja/dist/Naja"; +import {InteractionEvent} from "naja/dist/core/UIHandler"; + +export interface BaseRequestParams extends AjaxBaseRequestParams, Request { + url: string; + method: string; +} + +export interface BeforeEventDetail extends BaseBeforeEventDetail { + params: EventDetail & RequestParams; +} + +export interface InteractEventDetail< + E extends HTMLElement = HTMLElement +> extends BaseInteractEventDetail, EventDetail { + element: E; +} + +export interface SuccessEventDetail< + P = DatagridPayload +> extends BaseSuccessEventDetail, EventDetail { + params: BaseRequestParams; + payload: Payload

& NajaPayload; + response: AjaxResponse & Response; +} + +export interface ErrorEventDetail< + E extends Error = Error, +> extends BaseErrorEventDetail, EventDetail { + params: BaseRequestParams; + response: (AjaxResponse & Response) | undefined; + error: E; +} + +export interface AjaxEventMap extends BaseAjaxEventMap { + before: CustomEvent; + interact: CustomEvent; + snippetUpdate: CustomEvent; + success: CustomEvent; + error: CustomEvent; +} + +export class NajaAjax extends EventTarget implements Ajax { + constructor(public client: C) { + if (!client.VERSION || client.VERSION < 2) { + throw new Error("NajaAjax supports Naja 2 and higher" + (client.VERSION ? `(version ${client.VERSION} provided)` : '')) + } + super(); + } + + onInit() { + this.client.addEventListener('before', (e) => { + return this.dispatch('before', { + params: e.detail + }); + }) + + this.client.uiHandler.addEventListener('interaction', (e) => { + if (!(e.detail.element instanceof HTMLElement)) { + throw new Error("Element is not an instanceof HTMLElement"); + } + + return this.dispatch('interact', { + ...e.detail, + element: e.detail.element as HTMLElement // Naja's event has a type of HTMLElement + }) + }) + + + this.client.addEventListener('success', (e) => { + return this.dispatch('success', { + ...e.detail, + params: e.detail.request, + payload: e.detail.payload as Payload + }); + }) + + this.client.addEventListener('error', (e) => { + return this.dispatch('error', { + ...e.detail, + params: e.detail.request, + response: e.detail.response, + }); + }) + + return this; + } + + async request(args: RequestParams): Promise

{ + return await this.client.makeRequest(args.method, args.url, args.data) as P; + } + + async submitForm(element: E): Promise

{ + return await this.client.uiHandler.submitForm(element) as P; + } + + dispatch< + K extends string, M extends BaseAjaxEventMap = AjaxEventMap + >(type: K, detail: K extends keyof M ? EventDetail : any, options?: boolean): boolean { + return this.dispatchEvent(new CustomEvent(type, {detail})); + } + + declare addEventListener: ( + type: K, + listener: EventListener, + options?: boolean | AddEventListenerOptions + ) => void; + + declare removeEventListener: ( + type: K, + listener: EventListener, + options?: boolean | AddEventListenerOptions + ) => void; + + declare dispatchEvent: ( + event: K extends keyof M ? M[K] : CustomEvent + ) => boolean; +} diff --git a/assets/datagrid/assets/datagrid.css b/assets/datagrid/assets/datagrid.css new file mode 100644 index 0000000..8b096ce --- /dev/null +++ b/assets/datagrid/assets/datagrid.css @@ -0,0 +1,632 @@ +/* .datagrid--slide-toggle > td > div { + -webkit-transition: height .25s ease; + -o-transition: height .25s ease; + transition: height .25s ease; + overflow: hidden; +} */ + +.datagrid--content-row:not(.is-active) > td /*> div*/ { + display: none; +} + +@keyframes edited { + 0% { + background-color: #A6E2A9 + } + + 100% { + background-color: transparent + } + +} + +@keyframes edited-error { + 0% { + background-color: #E8AAA4 + } + + 100% { + background-color: transparent + } + +} + +.datagrid { + background-color: #fff; + padding: 1em; + box-sizing: border-box +} + +.datagrid .datagrid-input-group-full-width { + width: 100% +} + +.datagrid .hidden { + display: none !important +} + +.datagrid .datagrid-collapse-filters-button-row { + margin-bottom: 0.5em +} + +.datagrid .col-action .dropdown { + display: inline-block +} + +.datagrid .datagrid-row-inline-add.datagrid-row-inline-add-hidden { + display: none +} + +.datagrid .datagrid-row-columns-summary td { + border-top: 2px solid #bbb; + border-left: 1px solid #eee; + border-right: 1px solid #eee; + font-weight: bold +} + +.datagrid .datagrid-row-columns-summary td:first-child { + border-left: 1px solid #ddd +} + +.datagrid .datagrid-row-columns-summary td:last-child { + border-right: 1px solid #ddd +} + +.datagrid .datagrid-toolbar { + margin-top: .35em; + float: right; + display: inline-block +} + +.datagrid .datagrid-toolbar > span { + margin-left: 1em +} + +.datagrid .datagrid-toolbar > span > a { + margin-left: 0.5em +} + +.datagrid-toolbar .fa-square, .datagrid-toolbar .fa-check-square { + font-weight: normal; +} + +.datagrid .datagrid-exports .btn { + margin-left: 0.5em +} + +.datagrid .datagrid-exports .btn:first-child { + margin-left: 0 +} + +.datagrid .datagrid-settings { + display: inline-block +} + +.datagrid .datagrid-settings .dropdown-menu--grid { + font-size: 12px +} + +.datagrid .datagrid-settings .dropdown-menu--grid li .fa { + margin-right: 0.5em +} + +.datagrid .row-reset-filter { + text-align: right; + margin-bottom: 0.5em +} + +.datagrid .row-filters .datagrid-row-outer-filters-group { + margin-bottom: 0.5em +} + +.datagrid .datagrid-manual-submit { + margin-bottom: 0.5em +} + +.datagrid .filter-range-delimiter { + text-align: center +} + +.datagrid .bootstrap-select.input-sm > .btn { + padding: 5px 25px 5px 10px; + font-size: 12px; + line-height: 1.5; + border-radius: 3px +} + +.datagrid table { + margin: 0 +} + +.datagrid table thead tr .bootstrap-select:not([class*=col-]):not(.input-group-btn) { + width: auto +} + +.datagrid table thead tr .bootstrap-select:not([class*=col-]):not(.input-group-btn) > .btn { + width: auto +} + +.datagrid table thead tr .bootstrap-select:not([class*=col-]):not(.input-group-btn) .dropdown-menu li { + font-size: 13px +} + +.datagrid table thead tr.row-group-actions th { + border-bottom-width: 0 !important; + background-color: #f9f9f9 +} + +.datagrid table thead tr.row-group-actions .datagrid-selected-rows-count { + margin-left: 0.3em +} + +.datagrid table thead tr th { + font-size: 90%; + vertical-align: top +} + +.datagrid table thead tr th hr { + margin: 8px -8px +} + +.datagrid table thead tr th .datagrid-column-header-additions { + float: right +} + +.datagrid table thead tr th .datagrid-column-header-additions a[data-datagrid-reset-filter-by-column] { + margin-left: 0.3em; + color: #858585 +} + +.datagrid table thead tr th .datagrid-column-header-additions .column-settings-menu { + opacity: 0; + cursor: pointer; + margin-left: 0.3em; + display: inline-block +} + +.datagrid table thead tr th .datagrid-column-header-additions .column-settings-menu .dropdown-menu { + font-size: 12px +} + +.datagrid table thead tr th .datagrid-column-header-additions .column-settings-menu .dropdown-menu li .fa { + margin-right: 0.5em +} + +.datagrid table thead tr th .datagrid-column-header-additions .column-settings-menu .dropdown-toggle::after { + display: none !important +} + +.datagrid .datagrid-col-filter-date-range { + width: auto; + position: relative; + display: flex; + flex-wrap: wrap; + align-items: stretch; +} + +.datagrid .datagrid-col-filter-date-range > .input-group { + position: relative; + -ms-flex: 1 1 auto; + flex: 1 1 auto; + width: 1%; + margin-bottom: 0; +} + +.datagrid .datagrid-col-filter-datte-range-delimiter { + background-color: inherit; + border: none; + padding: .25rem .5rem +} + +.datagrid table thead tr th .datagrid-col-filter-range .form-control { + -webkit-border-radius: 3px; + -moz-border-radius: 3px; + border-radius: 3px +} + +.datagrid table thead tr th:hover .column-settings-menu { + opacity: 1 +} + +.datagrid table tbody td { + vertical-align: middle +} + +.datagrid table tbody tr.ui-sortable-helper { + display: table +} + +.datagrid table tbody tr .datagrid-inline-edit .form-control { + margin: -3px; + padding-bottom: 4px; + padding-top: 4px; + height: 28px +} + +.datagrid table tbody tr td[data-datagrid-editable-url].editing textarea { + padding: 2px; + margin: -3px +} + +.datagrid table tbody tr td.edited { + animation-name: edited; + animation-duration: 1.2s; + animation-delay: 0 +} + +.datagrid table tbody tr td.edited-error { + animation-name: edited-error; + animation-duration: 1.6s; + animation-delay: 0 +} + +.datagrid table th.col-checkbox, .datagrid table td.col-checkbox { + padding: 0; + width: 2.1em; + text-align: center; + vertical-align: middle +} + +.datagrid table th.col-checkbox .happy-checkbox, .datagrid table td.col-checkbox .happy-checkbox { + margin-right: 0 +} + +.datagrid table th.col-checkbox.col-checkbox-first, .datagrid table td.col-checkbox.col-checkbox-first { + border-top-color: transparent +} + +.datagrid table th.col-checkbox { + background-color: #f9f9f9 +} + +.datagrid table th.col-action, .datagrid table td.col-action { + white-space: nowrap; + width: 10px +} + +.datagrid table th.col-action { + text-align: center +} + +.datagrid table td.col-action { + text-align: right +} + +.datagrid table th.datagrid-fit-content, .datagrid table td.datagrid-fit-content { + width: 1%; + white-space: nowrap +} + +.datagrid .datagrid-tree > .datagrid-tree-header .datagrid-tree-item-right-actions-action { + opacity: 0 +} + +.datagrid .datagrid-tree > .datagrid-tree-item { + margin-left: 20px +} + +.datagrid .datagrid-tree .datagrid-tree-item { + position: relative +} + +.datagrid .datagrid-tree .datagrid-tree-item.ui-sortable-placeholder { + visibility: visible !important; + background-color: rgba(70, 83, 93, 0.1) +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content { + position: relative; + display: flex; + flex-direction: row; + flex-wrap: nowrap; + justify-content: space-between; + box-sizing: border-box; + height: 37px; + box-shadow: inset 0px -1px 1px -1px #9B9B9B +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left, .datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right { + display: flex; + flex-direction: row; + flex-wrap: nowrap; + justify-content: space-between; + align-items: center +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left { + order: 1 +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left > .chevron { + -webkit-border-radius: 11px; + -moz-border-radius: 11px; + border-radius: 11px; + width: 22px; + height: 22px; + line-height: 20px; + vertical-align: middle; + background-color: #fff; + display: inline-block; + text-align: center; + position: relative; + margin: 0 5px 0 -27px; + transition: transform 0.2s ease-in-out +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left > .chevron:hover { + -webkit-box-shadow: 0px 0px 3px 0px #b4b4b4; + -moz-box-shadow: 0px 0px 3px 0px #b4b4b4; + box-shadow: 0px 0px 3px 0px #b4b4b4 +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left > .chevron.toggle-rotate { + transform: rotate(90deg) +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left > .chevron .fa { + font-size: 10px; + transform: translate(1px, 0) +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right { + position: relative; + order: 2; + flex-basis: 50%; + display: flex; + flex-wrap: nowrap; + justify-content: flex-end; + flex-direction: row +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .btn { + margin-top: -3px +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-columns { + white-space: nowrap; + display: flex; + flex-basis: 70%; + flex-direction: row; + flex-wrap: nowrap; + justify-content: flex-end +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-columns .datagrid-tree-item-right-columns-column { + padding: 0 7px; + margin-right: 4px; + flex-basis: 25% +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-columns .datagrid-tree-item-right-columns-column:last-child { + margin-right: 0 +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-actions { + margin-left: 7px; + display: flex; + flex-direction: row; + flex-wrap: nowrap; + justify-content: space-between; + align-items: center +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-actions .datagrid-tree-item-right-actions-action { + margin-right: 4px +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-actions .datagrid-tree-item-right-actions-action:last-child { + margin-right: 0 +} + +.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-children:not(.datagrid-tree) { + margin-left: 28px +} + +.datagrid .datagrid-tree .datagrid-tree-item:not(.has-children) > .datagrid-tree-item-children { + box-sizing: border-box; + position: relative; + width: calc(100% - 28px); + min-height: 9px; + margin-top: -9px +} + +.datagrid .datagrid-tree .datagrid-tree-item.has-children > .datagrid-tree-item-children { + display: none +} + +.datagrid .datagrid-tree .datagrid-tree-item.has-children > .datagrid-tree-item-children .datagrid-tree-item-right { + flex-basis: calc(50% + 14px) +} + +.datagrid .datagrid-tree-item-children .datagrid-tree-item-right { + flex-basis: calc(50% + 14px) +} + +.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { + flex-basis: calc(50% + 28px) !important +} + +.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { + flex-basis: calc(50% + 42px) !important +} + +.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { + flex-basis: calc(50% + 56px) !important +} + +.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { + flex-basis: calc(50% + 74px) !important +} + +.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { + flex-basis: calc(50% + 88px) !important +} + +.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { + flex-basis: calc(50% + 102px) !important +} + +.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { + flex-basis: calc(50% + 116px) !important +} + +.datagrid .btn { + transition: all 0.1s ease-in-out; + white-space: nowrap +} + +.datagrid select { + padding: 0; + text-transform: none +} + +.datagrid .row-grid-bottom { + font-size: 0; + padding: 8px; + background-color: #f9f9f9; + border: 1px solid #ddd; + border-top: 0 +} + +.datagrid .row-grid-bottom .col-items { + font-size: 14px; + display: inline-block; + width: 25% +} + +.datagrid .row-grid-bottom .col-pagination { + font-size: 14px; + display: inline-block; + width: 50% +} + +.datagrid .row-grid-bottom .col-per-page { + font-size: 14px; + display: inline-block; + width: 25% +} + +.datagrid .row-grid-bottom .col-per-page form { + display: inline-block +} + +.datagrid .row-grid-bottom .col-per-page .form-control { + width: auto; + display: inline-block +} + +.datagrid .row-grid-bottom .datagrid-per-page-submit { + position: absolute; + visibility: hidden; + width: 0; + top: -200px +} + +.datagrid .pagination.active > span { + color: #fff +} + +.datagrid .pagination > a.disabled { + color: #989898; + cursor: not-allowed +} + +.datagrid .pagination > a.active { + pointer-events: none; + cursor: default +} + +.datagrid .row-group-actions th { + font-weight: normal +} + +.datagrid .col-checkbox { + -webkit-touch-callout: none; + -webkit-user-select: none; + -khtml-user-select: none; + -moz-user-select: none; + -ms-user-select: none; + user-select: none +} + +.datagrid .col-checkbox .happy-checkbox { + margin-top: 2px +} + +.datagrid .datagrid-column-status-option-icon { + float: right +} + +@media (min-width: 768px) { + .datagrid .ublaboo-datagrid-th-form-inline .form-group { + display: inline-block; + margin-bottom: 0; + vertical-align: middle + } + + .datagrid .ublaboo-datagrid-th-form-inline .form-control { + display: inline-block; + width: auto; + vertical-align: middle + } + + .datagrid .ublaboo-datagrid-th-form-inline .form-control[hidden] { + display: none; + } + + .ublaboo-datagrid-th-form-inline .form-control[hidden] { + display: none; + } + + .datagrid .ublaboo-datagrid-th-form-inline .input-group { + display: inline-table; + vertical-align: middle + } + + .datagrid .ublaboo-datagrid-th-form-inline .input-group .form-control { + width: auto + } + + .datagrid .ublaboo-datagrid-th-form-inline .input-group > .form-control { + width: 100% + } + + .datagrid .input-group-text { + height: calc(1.5em + 0.5rem + 2px); + } + + .datagrid .ublaboo-datagrid-th-form-inline .control-label { + margin-bottom: 0; + vertical-align: middle + } + + .datagrid .ublaboo-datagrid-th-form-inline .radio, .datagrid .ublaboo-datagrid-th-form-inline .checkbox { + display: inline-block; + margin-top: 0; + margin-bottom: 0; + vertical-align: middle + } + + .datagrid .ublaboo-datagrid-th-form-inline .radio label, .datagrid .ublaboo-datagrid-th-form-inline .checkbox label { + padding-left: 0 + } + + .datagrid .ublaboo-datagrid-th-form-inline .radio input[type="radio"], .datagrid .ublaboo-datagrid-th-form-inline .checkbox input[type="checkbox"] { + position: relative; + margin-left: 0 + } + +} + +.datagrid .btn-xs, .datagrid .btn-group-xs > .btn { + padding: 1px 5px; + font-size: 12px; + line-height: 1.5; + border-radius: 3px +} + +.datagrid .dropdown-item { + padding: 3px 20px; + line-height: 1.42857143; + font-size: 12px; +} diff --git a/assets/datagrid/assets/happy.css.ts b/assets/datagrid/assets/happy.css.ts new file mode 100644 index 0000000..525ffbc --- /dev/null +++ b/assets/datagrid/assets/happy.css.ts @@ -0,0 +1,464 @@ +export const happyStyles = `/** + * From happy-inputs by paveljanda: + * https://github.com/paveljanda/happy/blob/94357b7146b5f3029cc565859a588c5832dd374a/src/happy.css + */ + +.happy-color, +.happy-checkbox, +.happy-radio { + color: #333333; +} + +.happy-color > b, +.happy-checkbox > b, +.happy-radio > b { + background-color: #333333; +} + +.happy-color.active, +.active.happy-checkbox, +.active.happy-radio { + color: #333333; +} + +.happy-color.active > b, +.active.happy-checkbox > b, +.active.happy-radio > b { + background-color: #333333; +} + +.happy-color.primary, +.primary.happy-checkbox, +.primary.happy-radio { + color: #333333; +} + +.happy-color.primary > b, +.primary.happy-checkbox > b, +.primary.happy-radio > b { + background-color: #333333; +} + +.happy-color.primary.active, +.primary.active.happy-checkbox, +.primary.active.happy-radio { + color: #4c86bb; +} + +.happy-color.primary.active > b, +.primary.active.happy-checkbox > b, +.primary.active.happy-radio > b { + background-color: #4c86bb; +} + +.happy-color.success, +.success.happy-checkbox, +.success.happy-radio { + color: #333333; +} + +.happy-color.success > b, +.success.happy-checkbox > b, +.success.happy-radio > b { + background-color: #333333; +} + +.happy-color.success.active, +.success.active.happy-checkbox, +.success.active.happy-radio { + color: #72b889; +} + +.happy-color.success.active > b, +.success.active.happy-checkbox > b, +.success.active.happy-radio > b { + background-color: #72b889; +} + +.happy-color.info, +.info.happy-checkbox, +.info.happy-radio { + color: #333333; +} + +.happy-color.info > b, +.info.happy-checkbox > b, +.info.happy-radio > b { + background-color: #333333; +} + +.happy-color.info.active, +.info.active.happy-checkbox, +.info.active.happy-radio { + color: #5bc0de; +} + +.happy-color.info.active > b, +.info.active.happy-checkbox > b, +.info.active.happy-radio > b { + background-color: #5bc0de; +} + +.happy-color.warning, +.warning.happy-checkbox, +.warning.happy-radio { + color: #333333; +} + +.happy-color.warning > b, +.warning.happy-checkbox > b, +.warning.happy-radio > b { + background-color: #333333; +} + +.happy-color.warning.active, +.warning.active.happy-checkbox, +.warning.active.happy-radio { + color: #f0bb65; +} + +.happy-color.warning.active > b, +.warning.active.happy-checkbox > b, +.warning.active.happy-radio > b { + background-color: #f0bb65; +} + +.happy-color.danger, +.danger.happy-checkbox, +.danger.happy-radio { + color: #333333; +} + +.happy-color.danger > b, +.danger.happy-checkbox > b, +.danger.happy-radio > b { + background-color: #333333; +} + +.happy-color.danger.active, +.danger.active.happy-checkbox, +.danger.active.happy-radio { + color: #ed6b6b; +} + +.happy-color.danger.active > b, +.danger.active.happy-checkbox > b, +.danger.active.happy-radio > b { + background-color: #ed6b6b; +} + +.happy-color.white, +.white.happy-checkbox, +.white.happy-radio { + color: #333333; +} + +.happy-color.white > b, +.white.happy-checkbox > b, +.white.happy-radio > b { + background-color: #333333; +} + +.happy-color.white.active, +.white.active.happy-checkbox, +.white.active.happy-radio { + color: #ffffff; +} + +.happy-color.white.active > b, +.white.active.happy-checkbox > b, +.white.active.happy-radio > b { + background-color: #ffffff; +} + +.happy-border-color, +.happy-radio { + border-color: rgba(51, 51, 51, 0.8); +} + +.happy-border-color.active, +.active.happy-radio { + border-color: #333333; +} + +.happy-border-color.primary, +.primary.happy-radio { + border-color: rgba(51, 51, 51, 0.8); +} + +.happy-border-color.primary.active, +.primary.active.happy-radio { + border-color: #4c86bb; +} + +.happy-border-color.success, +.success.happy-radio { + border-color: rgba(51, 51, 51, 0.8); +} + +.happy-border-color.success.active, +.success.active.happy-radio { + border-color: #72b889; +} + +.happy-border-color.info, +.info.happy-radio { + border-color: rgba(51, 51, 51, 0.8); +} + +.happy-border-color.info.active, +.info.active.happy-radio { + border-color: #5bc0de; +} + +.happy-border-color.warning, +.warning.happy-radio { + border-color: rgba(51, 51, 51, 0.8); +} + +.happy-border-color.warning.active, +.warning.active.happy-radio { + border-color: #f0bb65; +} + +.happy-border-color.danger, +.danger.happy-radio { + border-color: rgba(51, 51, 51, 0.8); +} + +.happy-border-color.danger.active, +.danger.active.happy-radio { + border-color: #ed6b6b; +} + +.happy-border-color.white, +.white.happy-radio { + border-color: rgba(51, 51, 51, 0.8); +} + +.happy-border-color.white.active, +.white.active.happy-radio { + border-color: #ffffff; +} + +/** + * Common + */ + +input[type="radio"].happy, +input[type="checkbox"].happy { + position: absolute; + top: -50%; + left: -50%; + opacity: 0; +} + +label:not(.selectable), +.noselect { + -webkit-touch-callout: none; + -webkit-user-select: none; + -khtml-user-select: none; + -moz-user-select: none; + -ms-user-select: none; + user-select: none; +} + +label { + cursor: pointer; + position: relative; +} + +/** + * Checkbox + */ + +.happy-checkbox { + border-color: #333333; + margin-right: 0.2em; + position: relative; + display: inline-block; + line-height: 20px; + vertical-align: middle; + width: 16px; + height: 16px; + border-width: 2px; + border-style: solid; + cursor: pointer; + box-sizing: border-box; + top: -2px; + -webkit-border-radius: 2.66667px; + -moz-border-radius: 2.66667px; + border-radius: 2.66667px; +} + +.happy-checkbox svg { + position: absolute; + display: block; + top: -2px; + left: -2px; + height: 16px; + width: 16px; + opacity: 0; + -webkit-border-radius: 2.66667px; + -moz-border-radius: 2.66667px; + border-radius: 2.66667px; + background-color: #333333; + -ms-transform: scale(0.4); + -webkit-transform: scale(0.4); + transform: scale(0.4); + -ms-transition: all 180ms; + -webkit-transition: all 180ms; + transition: all 180ms; +} + +.happy-checkbox svg rect { + fill: white; +} + +.happy-checkbox svg rect:first-child { + -ms-transform: rotate(45deg); + -webkit-transform: rotate(45deg); + transform: rotate(45deg); +} + +.happy-checkbox svg rect:nth-child(2) { + -ms-transform: rotate(-45deg); + -webkit-transform: rotate(-45deg); + transform: rotate(-45deg); + /* fill: yellow; */ +} + +.happy-checkbox.thin { + border-width: 1px; +} + +.happy-checkbox.thin svg { + top: -1px; + left: -1px; +} + +.happy-checkbox.white { + border-color: #ffffff; +} + +.happy-checkbox.gray-border { + border-color: #858585; +} + +.happy-checkbox.primary-border { + border-color: #4c86bb; +} + +.happy-checkbox.success-border { + border-color: #72b889; +} + +.happy-checkbox.info-border { + border-color: #5bc0de; +} + +.happy-checkbox.warning-border { + border-color: #f0bb65; +} + +.happy-checkbox.danger-border { + border-color: #ed6b6b; +} + +.happy-checkbox.primary svg { + background-color: #4c86bb; +} + +.happy-checkbox.success svg { + background-color: #72b889; +} + +.happy-checkbox.info svg { + background-color: #5bc0de; +} + +.happy-checkbox.warning svg { + background-color: #f0bb65; +} + +.happy-checkbox.danger svg { + background-color: #ed6b6b; +} + +.happy-checkbox.white svg { + background-color: #ffffff; +} + +.happy-checkbox.white svg rect { + fill: #333333; +} + +.happy-checkbox.active { + border-color: transparent; +} + +.happy-checkbox.active svg { + opacity: 1; + -ms-transform: scale(1); + -webkit-transform: scale(1); + transform: scale(1); +} + +/** + * Radio + */ + +.happy-radio { + position: relative; + display: inline-block; + line-height: 20px; + vertical-align: middle; + width: 16px; + height: 16px; + border-width: 2px; + border-style: solid; + cursor: pointer; + box-sizing: border-box; + top: -2px; + -webkit-border-radius: 16px; + -moz-border-radius: 16px; + border-radius: 16px; +} + +.happy-radio.thin { + border-width: 1.66667px; +} + +.happy-radio b { + position: absolute; + display: block; + top: 2px; + left: 2px; + bottom: 2px; + right: 2px; + opacity: 0; + -webkit-border-radius: 10.66667px; + -moz-border-radius: 10.66667px; + border-radius: 10.66667px; + -ms-transform: scale(0.4); + -webkit-transform: scale(0.4); + transform: scale(0.4); + -ms-transition: all 180ms; + -webkit-transition: all 180ms; + transition: all 180ms; +} + +.happy-radio.active b { + opacity: 1; + -ms-transform: scale(1); + -webkit-transform: scale(1); + transform: scale(1); +} + +.happy-radio.focus { + outline: none; + -webkit-box-shadow: 0px 0px 5px 0px rgba(50, 50, 50, 0.75); + -moz-box-shadow: 0px 0px 5px 0px rgba(50, 50, 50, 0.75); + box-shadow: 0px 0px 5px 0px rgba(50, 50, 50, 0.75); +} +`; diff --git a/assets/datagrid/datagrid.ts b/assets/datagrid/datagrid.ts new file mode 100644 index 0000000..337ed32 --- /dev/null +++ b/assets/datagrid/datagrid.ts @@ -0,0 +1,152 @@ +import {defaultDatagridNameResolver, isEnter} from "@datagrid/utils"; +import type { + DatagridEventMap, + EventListener, + Ajax, + DatagridOptions, EventDetail, +} from "@datagrid/types"; + +export class Datagrid extends EventTarget { + private static readonly defaultOptions: DatagridOptions = { + confirm: confirm, + resolveDatagridName: defaultDatagridNameResolver, + plugins: [], + }; + + public readonly name: string; + + public readonly ajax: Ajax; + + private readonly options: DatagridOptions; + + constructor( + public readonly el: HTMLElement, + ajax: Ajax | ((grid: Datagrid) => Ajax), + options: Partial + ) { + super(); + + this.options = { + ...Datagrid.defaultOptions, + ...options, + }; + + const name = this.resolveDatagridName(); + + if (!name) { + throw new Error("Cannot resolve name of a datagrid!"); + } + + this.name = name; + + this.ajax = typeof ajax === "function" ? ajax(this) : ajax; + + this.ajax.addEventListener("success", e => { + if (e.detail.payload?._datagrid_name === this.name && e.detail.payload?._datagrid_init) { + this.init(); + } + }); + + this.init(); + } + + public init() { + console.log("init") + + let cancelled = !this.dispatch('beforeInit', {datagrid: this}) + if (!cancelled) { + this.options.plugins.forEach((plugin) => { + plugin.onDatagridInit?.(this) + }) + } + + // Uncheck toggle-all + const checkedRows = this.el.querySelectorAll("input[data-check]:checked"); + if (checkedRows.length === 1 && checkedRows[0].getAttribute("name") === "toggle-all") { + const input = checkedRows[0]; + if (input) { + input.checked = false; + } + } + + this.el.querySelectorAll("input[data-datagrid-manualsubmit]").forEach(inputEl => { + const form = inputEl.closest("form"); + if (!form) return; + + inputEl.addEventListener("keydown", e => { + if (!isEnter(e)) return; + + e.stopPropagation(); + e.preventDefault(); + return this.ajax.submitForm(form); + }); + }); + + this.ajax.addEventListener("success", ({detail: {payload}}) => { + // todo: maybe move? + if (payload._datagrid_name && payload._datagrid_name === this.name) { + this.el.querySelector("[data-datagrid-reset-filter-by-column]") + ?.classList.add("hidden"); + + if (payload.non_empty_filters && payload.non_empty_filters.length >= 1) { + const resets = Array.from(this.el.querySelectorAll( + `[data-datagrid-reset-filter-by-column]` + )); + + const getColumnName = (el: HTMLElement) => el.getAttribute( + "data-datagrid-reset-filter-by-column" + ) + + /// tf? + for (const columnName of payload.non_empty_filters) { + resets.find(getColumnName)?.classList.remove("hidden"); + } + + const href = this.el.querySelector(".reset-filter") + ?.getAttribute("href"); + + if (href) { + resets.forEach((el) => { + const columnName = getColumnName(el); + + const newHref = href.replace("-resetFilter", "-resetColumnFilter"); + el.setAttribute("href", `${newHref}&${this.name}-key=${columnName}`); + }) + } + } + } + }) + + this.dispatch('afterInit', {datagrid: this}); + } + + public confirm(message: string): boolean { + return this.options.confirm.bind(this)(message); + } + + public resolveDatagridName(): string | null { + return this.options.resolveDatagridName.bind(this)(this.el); + } + + dispatch< + K extends string, M extends DatagridEventMap = DatagridEventMap + >(type: K, detail: K extends keyof M ? EventDetail : any, options?: boolean): boolean { + return this.dispatchEvent(new CustomEvent(type, {detail})); + } + + declare addEventListener: ( + type: K, + listener: EventListener, + options?: boolean | AddEventListenerOptions + ) => void; + + declare removeEventListener: ( + type: K, + listener: EventListener, + options?: boolean | AddEventListenerOptions + ) => void; + + declare dispatchEvent: ( + event: K extends keyof M ? M[K] : CustomEvent + ) => boolean; +} diff --git a/assets/datagrid/datagrids.ts b/assets/datagrid/datagrids.ts new file mode 100644 index 0000000..2240727 --- /dev/null +++ b/assets/datagrid/datagrids.ts @@ -0,0 +1,85 @@ +import {Datagrid} from "@datagrid/datagrid"; +import { + AutosubmitPlugin, + CheckboxPlugin, + ConfirmPlugin, + HappyPlugin, + InlinePlugin, + UrlPlugin, + SortablePlugin, + NetteFormsPlugin, + SelectpickerPlugin +} from "@datagrid/plugins"; +import {Ajax, DatagridsOptions} from "@datagrid/types"; +import {SortableJS} from "@datagrid/integrations/sortable-js"; +import {DatepickerPlugin} from "@datagrid/plugins/integrations/datepicker"; +import {BootstrapSelect, Happy, VanillaDatepicker} from "@datagrid/integrations"; + +export class Datagrids { + private datagrids: Datagrid[] = []; + + readonly options: DatagridsOptions; + + readonly root: HTMLElement; + + constructor(readonly ajax: Ajax, options: Partial = {}) { + this.options = { + selector: "div.datagrid[data-refresh-state]", + datagrid: {}, + root: document.body, + ...options, + }; + + const root = typeof this.options.root === "string" + ? document.querySelector(this.options.root) + : this.options.root; + + if (!root || !(root instanceof HTMLElement)) { + throw new Error("Root element not found or is not an HTMLElement"); + } + + this.root = root; + + this.init(); + } + + init() { + this.ajax.onInit(); + (this.options.datagrid?.plugins ?? []).forEach((plugin) => plugin.onInit?.(this)); + + this.initDatagrids(); + } + + initDatagrids() { + this.datagrids = Array.from(this.root.querySelectorAll(this.options.selector)).map( + datagrid => new Datagrid(datagrid, this.ajax, this.options.datagrid) + ); + } +} + +export const createDatagrids = (ajax: Ajax, _options: Partial = {}) => { + return new Datagrids(ajax, _options); +}; + +/** + * @deprecated Include plugins manually with createDatagrids + */ +export const createFullDatagrids = (ajax: Ajax, _options: Partial = {}) => { + return createDatagrids(ajax, { + datagrid: { + plugins: [ + new AutosubmitPlugin(), + new CheckboxPlugin(), + new ConfirmPlugin(), + new InlinePlugin(), + // new UrlPlugin(), + new NetteFormsPlugin(), + new HappyPlugin(new Happy()), + new SortablePlugin(new SortableJS()), + new DatepickerPlugin(new VanillaDatepicker()), + new SelectpickerPlugin(new BootstrapSelect()) + ], + }, + ..._options, + }) +}; diff --git a/assets/datagrid/index.ts b/assets/datagrid/index.ts new file mode 100644 index 0000000..39d8538 --- /dev/null +++ b/assets/datagrid/index.ts @@ -0,0 +1,6 @@ +export * from "./datagrid"; +export * from "./plugins"; +export * from "./integrations"; + +export * from "./datagrids" +export * from "./datagrid"; diff --git a/assets/datagrid/integrations/bootstrap-select.ts b/assets/datagrid/integrations/bootstrap-select.ts new file mode 100644 index 0000000..28dc39c --- /dev/null +++ b/assets/datagrid/integrations/bootstrap-select.ts @@ -0,0 +1,46 @@ +import {Selectpicker} from "@datagrid/types"; +import {window} from "@datagrid/utils"; + +/** + * @deprecated subject for replacement & removal + */ +export class BootstrapSelect implements Selectpicker { + initSelectpickers(elements: HTMLElement[]): void { + if (window().jQuery) { + const $ = window().jQuery; + if ($?.fn.selectpicker) { + $.fn.selectpicker.defaults = { + countSelectedText: elements[0].getAttribute("i18n-selected") ?? "", + iconBase: "fa", + tickIcon: elements[0].getAttribute("selected-icon-check") ?? "fa fa-check", + }; + + elements.forEach(element => + $(element) + .removeClass("form-select form-select-sm") + .addClass("form-control form-control-sm") + .selectpicker("destroy") + .selectpicker({}) + ); + + Array.from(elements) + .filter(element => element.hasAttribute("data-datagrid-multiselect-id")) + .forEach(element => { + const $picker = $(element); + const $parent = $picker.parent(); + + $picker.removeAttr("id"); + const id = element.getAttribute("data-datagrid-multiselect-id"); + + $picker.on("loaded.bs.select", () => { + $parent.attr("style", "display: none;"); + $parent.find(".hidden").removeClass("hidden").addClass("btn-default btn-secondary"); + }); + + $picker.on("rendered.bs.select", () => $parent.attr("id", id)); + }); + } + } + } + +} diff --git a/assets/datagrid/integrations/happy.ts b/assets/datagrid/integrations/happy.ts new file mode 100644 index 0000000..1c8a755 --- /dev/null +++ b/assets/datagrid/integrations/happy.ts @@ -0,0 +1,222 @@ +import {happyStyles} from "@datagrid/assets/happy.css"; + +/** + * Slightly cleaned up & typed version of happy-inputs by paveljanda. + */ +export class Happy { + private colors: string[] = ["primary", "success", "info", "warning", "danger", "white", "gray"]; + + private templates = { + radio: '

', + checkbox: + '
', + text: "", + textarea: "", + }; + + init() { + if (!document.querySelector('[data-happy-stylesheet]')) { + document.head.append(``) + } + this.removeBySelector(".happy-radio"); + this.removeBySelector(".happy-checkbox"); + + this.initRadio(); + this.initCheckbox(); + } + + /** + * @deprecated + */ + reset() { + this.init(); + } + + addColorToInput(input: HTMLElement, happyInput: HTMLElement, classString: string) { + if (input.classList.contains(classString)) { + happyInput.classList.add(classString); + } + + classString = `${classString}-border`; + + if (input.classList.contains(classString)) { + happyInput.classList.add(classString); + } + } + + // i... you know what, no, let "thinkess" be "thinkess" + addThinkessToInput(input: HTMLElement, happyInput: HTMLElement) { + if (input.classList.contains("thin")) { + happyInput.classList.add("thin"); + } + } + + setNames(input: HTMLElement, happyInput: HTMLElement) { + happyInput.setAttribute("data-name", input.getAttribute("name") ?? ""); + + var value = input.getAttribute("value"); + + if (value !== "undefined" && value !== null) { + happyInput.setAttribute("data-value", input.getAttribute("value") ?? ""); + } + } + + removeBySelector(selector: string) { + document.querySelectorAll(selector).forEach(el => el.parentNode?.removeChild(el)); + } + + initRadio() { + document.querySelectorAll("input[type=radio].happy").forEach(input => { + /** + * Paste happy component into html + */ + input.insertAdjacentHTML("afterend", this.templates.radio); + + const happyInput = input.nextElementSibling; + + if (happyInput instanceof HTMLElement) { + /** + * Add optional colors + */ + this.colors.forEach(color => { + this.addColorToInput(input, happyInput, color); + this.setNames(input, happyInput); + }); + + this.addThinkessToInput(input, happyInput); + } + + /** + * Init state + */ + this.checkRadioState(input); + + /** + * Set aciton functionality for native change + */ + document.addEventListener("change", this.radioOnChange.bind(this)); + }); + } + + initCheckbox() { + document.querySelectorAll("input[type=checkbox].happy").forEach(input => { + /** + * Paste happy component into html + */ + input.insertAdjacentHTML("afterend", this.templates.checkbox); + + const happyInput = input.nextElementSibling; + + /** + * Add optional colors + */ + if (happyInput instanceof HTMLElement) { + this.colors.forEach(color => { + this.addColorToInput(input, happyInput, color); + this.setNames(input, happyInput); + }); + + this.addThinkessToInput(input, happyInput); + } + + /** + * Init state + */ + this.checkCheckboxState(input); + + /** + * Set action functionality for click || native change + */ + document.addEventListener("click", this.checkCheckboxStateOnClick.bind(this)); + document.addEventListener("change", this.checkCheckboxStateOnChange.bind(this)); + }); + } + + checkCheckboxStateOnClick(event: Event) { + const target = event.target; + + // When target is SVGSVGElement (), return parentNode, + // When target is a SVGGraphicsElement (,...), find and return it's parent node + // otherwise return target itself. + const happyInput = + target instanceof SVGSVGElement + ? target.parentNode + : target instanceof SVGGraphicsElement + ? target.closest("svg")?.parentNode + : target; + + if (!(happyInput instanceof HTMLElement) || !happyInput.classList.contains("happy-checkbox")) { + return; + } + + event.preventDefault(); + + const name = happyInput.getAttribute("data-name"); + const value = happyInput.getAttribute("data-value"); + + const input = document.querySelector( + `.happy-checkbox[data-name="${name}"]` + (!!value ? `[value="${value}"]` : "") + ); + if (!(input instanceof HTMLInputElement)) return; + + const checked = happyInput.classList.contains("active"); + + input.checked = !checked; + checked ? happyInput.classList.remove("active") : happyInput.classList.add("active"); + } + + checkCheckboxStateOnChange({ target }: Event) { + if (!(target instanceof HTMLInputElement)) return; + + if (target.classList.contains("happy")) { + this.checkCheckboxState(target); + } + } + + checkRadioState(input: HTMLInputElement) { + if (!input.checked || !input.hasAttribute("name")) return; + + const name = input.getAttribute("name"); + const value = input.getAttribute("value"); + + const element = document.querySelector( + `.happy-checkbox[data-name="${name}"]` + (!!value ? `[data-value="${value}"]` : "") + ); + + if (element) { + element.classList.add("active"); + } + } + + checkCheckboxState(input: HTMLInputElement) { + const name = input.getAttribute("name"); + if (!name) return; + + const value = input.getAttribute("value"); + const element = document.querySelector( + `.happy-checkbox[data-name="${name}"]` + (!!value ? `[data-value="${value}"]` : "") + ); + + if (!element) return; + + input.checked ? element.classList.add("active") : element.classList.remove("active"); + } + + radioOnChange({ target }: Event) { + // Check whether target is
${snippet}
`; + + childrenBlock.innerHTML = template; + } + //children_block.addClass('loaded'); + //children_block.slideToggle('fast'); + } + } + }) + return true; + } +} \ No newline at end of file diff --git a/assets/datagrid/plugins/index.ts b/assets/datagrid/plugins/index.ts new file mode 100644 index 0000000..99b83ae --- /dev/null +++ b/assets/datagrid/plugins/index.ts @@ -0,0 +1,12 @@ +export * from "./integrations/datepicker"; +export * from "./integrations/happy"; +export * from "./integrations/nette-forms" +export * from "./integrations/selectpicker"; +export * from "./integrations/sortable"; + +export * from "./features/autosubmit"; +export * from "./features/checkboxes"; +export * from "./features/confirm"; +export * from "./features/editable"; +export * from "./features/inline"; +export * from "./features/item-detail"; diff --git a/assets/datagrid/plugins/integrations/datepicker.ts b/assets/datagrid/plugins/integrations/datepicker.ts new file mode 100644 index 0000000..7e4a1c7 --- /dev/null +++ b/assets/datagrid/plugins/integrations/datepicker.ts @@ -0,0 +1,17 @@ +import {Datagrid} from "@datagrid"; +import {DatagridPlugin, Datepicker} from "@datagrid/types"; + +export class DatepickerPlugin implements DatagridPlugin { + constructor(private datepicker: Datepicker) { + } + + onDatagridInit(datagrid: Datagrid): boolean { + const elements = datagrid.el.querySelectorAll("input[data-provide='datepicker']"); + + if (elements.length >= 1) { + this.datepicker.initDatepickers(Array.from(elements), datagrid); + } + + return true; + } +} diff --git a/assets/datagrid/plugins/integrations/happy.ts b/assets/datagrid/plugins/integrations/happy.ts new file mode 100644 index 0000000..32605c0 --- /dev/null +++ b/assets/datagrid/plugins/integrations/happy.ts @@ -0,0 +1,19 @@ +import {Datagrid} from "@datagrid"; +import { DatagridPlugin } from "@datagrid/types"; +import { window } from "@datagrid/utils"; +import type {Happy} from "@datagrid/integrations"; + +export class HappyPlugin implements DatagridPlugin { + constructor(private happy?: Happy) { + } + + onDatagridInit(datagrid: Datagrid): boolean { + const happy = this.happy ?? window().happy ?? null; + + if (happy) { + happy.init(); + } + + return true; + } +} diff --git a/assets/datagrid/plugins/integrations/nette-forms.ts b/assets/datagrid/plugins/integrations/nette-forms.ts new file mode 100644 index 0000000..5ffbe75 --- /dev/null +++ b/assets/datagrid/plugins/integrations/nette-forms.ts @@ -0,0 +1,18 @@ +import {DatagridPlugin, Nette} from "@datagrid/types"; +import {Datagrid} from "@datagrid"; +import {window} from "@datagrid/utils"; + +export class NetteFormsPlugin implements DatagridPlugin { + constructor(private nette?: Nette) { + } + + onDatagridInit(datagrid: Datagrid): boolean { + const nette = this.nette ?? window().Nette ?? null; + + if (nette) { + datagrid.el.querySelectorAll("form").forEach(form => nette.initForm(form)); + } + + return true; + } +} diff --git a/assets/datagrid/plugins/integrations/selectpicker.ts b/assets/datagrid/plugins/integrations/selectpicker.ts new file mode 100644 index 0000000..ef63126 --- /dev/null +++ b/assets/datagrid/plugins/integrations/selectpicker.ts @@ -0,0 +1,17 @@ +import {DatagridPlugin, Selectpicker} from "@datagrid/types"; +import {Datagrid} from "@datagrid"; + +export class SelectpickerPlugin implements DatagridPlugin { + constructor(private selectpicker: Selectpicker) { + } + + onDatagridInit(datagrid: Datagrid): boolean { + const elements = datagrid.el.querySelectorAll(".selectpicker"); + + if (elements.length >= 1) { + this.selectpicker.initSelectpickers(Array.from(elements), datagrid); + } + + return true; + } +} diff --git a/assets/datagrid/plugins/integrations/sortable.ts b/assets/datagrid/plugins/integrations/sortable.ts new file mode 100644 index 0000000..4b69631 --- /dev/null +++ b/assets/datagrid/plugins/integrations/sortable.ts @@ -0,0 +1,62 @@ +import {Datagrid} from "@datagrid/datagrid"; +import { DatagridPlugin, Sortable } from "@datagrid/types"; +import {attachSlideToggle} from "@datagrid/utils"; + +export class SortablePlugin implements DatagridPlugin { + constructor(private sortable: Sortable) { + } + + onDatagridInit(datagrid: Datagrid): boolean { + datagrid.ajax.addEventListener('before', (event) => { + // TODO old ln 694... wtf? + }) + + this.sortable.initSortable(datagrid); + + datagrid.ajax.addEventListener('success', ({detail: {payload}}) => { + if (payload._datagrid_sort) { + for (const key in payload._datagrid_sort) { + const href = payload._datagrid_sort[key]; + const element = datagrid.el.querySelector(`#datagrid-sort-${key}`); + + if (element) { + // TODO: Only for BC support, to be removed + element.setAttribute("href", href); + + element.setAttribute("data-href", href); + } + } + this.sortable.initSortable(datagrid); + } + + if (payload._datagrid_tree) { + const childrenContainer = datagrid.el.querySelector( + `.datagrid-tree-item[data-id='${payload._datagrid_tree}'] .datagrid-tree-item-children` + ); + if (childrenContainer && payload.snippets) { + childrenContainer.classList.add("loaded"); + for (const key in payload.snippets) { + const snippet = payload.snippets[key]; + + const doc = new DOMParser().parseFromString(snippet, 'text/html'); + const element = doc.firstElementChild; + if (element) { + const treeItem = document.createElement("div"); + treeItem.id = key; + treeItem.classList.add("datagrid-tree-item") + treeItem.setAttribute("data-id", key); + if (element.hasAttribute("has-children")) { + treeItem.classList.add("has-children"); + } + + childrenContainer.append(treeItem); + // attachSlideToggle(childrenContainer); + } + } + } + this.sortable.initSortableTree(datagrid); + } + }) + return true; + } +} diff --git a/assets/datagrid/types/ajax.d.ts b/assets/datagrid/types/ajax.d.ts new file mode 100644 index 0000000..3262f37 --- /dev/null +++ b/assets/datagrid/types/ajax.d.ts @@ -0,0 +1,136 @@ +import {EventDetail, EventListener, EventMap} from "."; +import {Datagrid} from "@datagrid"; + +export interface BaseRequestParams { + method: "GET" | "HEAD" | "POST" | "PUT" | "DELETE" | "CONNECT" | "OPTIONS" | "TRACE" | "PATCH" | string; + url: string; +} + +export interface RequestParams extends BaseRequestParams { + data: D; +} + +export interface DatagridPayload { + _datagrid_name?: string; + _datagrid_toggle_detail?: string + _datagrid_inline_editing?: boolean; + _datagrid_inline_adding?: boolean; + _datagrid_inline_edited?: boolean; + _datagrid_inline_edit_cancel?: boolean; + _datagrid_url?: boolean; + _datagrid_sort?: Record; + _datagrid_tree?: string; + _datagrid_editable_new_value?: string; + _datagrid_redraw_item_id?: string; + _datagrid_redraw_item_class?: string; + _datagrid_init?: boolean; + non_empty_filters?: string[]; +} + +export interface DatagridState { + "grid-page": number | null, + "grid-perPage": number, + // TODO + "grid-sort": any | null, + "grid-filter": any | null +} + +export type Payload

= P & { + snippets?: Record; + redirect?: string; + state: S; +}; + +export interface Response { + headers: Record | Headers; + status: number; +} + +export interface BeforeEventDetail { + params: RequestParams; +} + +export interface InteractEventDetail { + element: E; +} + +export interface SuccessEventDetail

{ + params: BaseRequestParams; + payload: Payload

; + response: Response; +} + +export interface ErrorEventDetail { + params: BaseRequestParams; + response?: Response; + error?: E; +} + +export interface AjaxEventMap extends EventMap { + before: CustomEvent; + interact: CustomEvent; + snippetUpdate: CustomEvent; + success: CustomEvent; + error: CustomEvent; +} + +export interface Ajax extends EventTarget { + client: C; + + /** + * Initialization of the Ajax instance, called in createDatagrids(). + * @return this + */ + onInit(): this; + + /** + * Initializes a Datagrid instance. + * @param grid The Datagrid instance + */ + onDatagridInit?(grid: G): void; + + /** + * Sends a request to the server. + */ + request(args: RequestParams): Promise

; + + /** + * Submits a form + */ + submitForm(element: E): Promise

; + + /** + * Shortcut for dispatchEvent + * @internal + */ + dispatch( + type: K, + detail: K extends keyof M ? EventDetail : any, + options?: boolean + ): boolean; + + /** + * Note: For events dispatched directly from the underlying client, {@see Ajax.client}} + **/ + addEventListener( + type: K, + listener: EventListener, + options?: boolean | AddEventListenerOptions + ): void; + + /** + * Note: For events dispatched directly from the underlying client, {@see Ajax.client}} + **/ + removeEventListener( + type: K, + listener: EventListener, + options?: boolean | AddEventListenerOptions + ): void; + + /** + * @internal + */ + dispatchEvent( + event: K extends keyof M ? M[K] : CustomEvent + ): boolean; +} diff --git a/assets/datagrid/types/datagrid.d.ts b/assets/datagrid/types/datagrid.d.ts new file mode 100644 index 0000000..84e99b2 --- /dev/null +++ b/assets/datagrid/types/datagrid.d.ts @@ -0,0 +1,29 @@ +import {Datagrid, Datagrids} from "@datagrid"; +import {EventMap, Nette} from "@datagrid/types"; + +export interface DatagridEventDetail { + datagrid: Datagrid; +} + +export interface DatagridEventMap extends EventMap { + beforeInit: CustomEvent; + afterInit: CustomEvent; +} + +export interface DatagridPlugin { + onInit?(datagrids: Datagrids): void; + onDatagridInit?(datagrid: Datagrid): boolean; +} + +export interface DatagridOptions { + confirm(this: Datagrid, message: string): boolean; + // Returning null will skip this datagrid + resolveDatagridName: (this: Datagrid, datagrid: HTMLElement) => string | null; + plugins: DatagridPlugin[]; +} + +export interface DatagridsOptions { + datagrid: Partial; + selector: string; + root: HTMLElement | string; +} diff --git a/assets/datagrid/types/index.d.ts b/assets/datagrid/types/index.d.ts new file mode 100644 index 0000000..39a6073 --- /dev/null +++ b/assets/datagrid/types/index.d.ts @@ -0,0 +1,40 @@ +import { Happy } from "@datagrid/integrations"; +import TomSelect from "tom-select"; + +export interface Nette { + initForm: (form: HTMLFormElement) => void; +} + +export type Constructor = new (...args: any[]) => T; + +export type KeysOf = { [P in keyof T]: TVal; } + +export interface ExtendedWindow extends Window { + jQuery?: any; + Nette?: Nette; + TomSelect?: Constructor; + happy?: Happy; +} + +// https://github.com/naja-js/naja/blob/384d298a9199bf778985d1bcf5747fe8de305b22/src/utils.ts +type EventListenerFunction = ( + this: ET, + event: E +) => boolean | void | Promise; + +interface EventListenerObject { + handleEvent(event: E): void | Promise; +} + +export type EventListener = + | EventListenerFunction + | EventListenerObject + | null; + +export type EventDetail = E extends CustomEvent ? D : never; + +export interface EventMap extends Record {} + +export * from "./datagrid"; +export * from "./integrations"; +export * from "./ajax"; diff --git a/assets/datagrid/types/integrations.d.ts b/assets/datagrid/types/integrations.d.ts new file mode 100644 index 0000000..16e7edd --- /dev/null +++ b/assets/datagrid/types/integrations.d.ts @@ -0,0 +1,14 @@ +import {Datagrid} from "@datagrid"; + +export interface Sortable { + initSortable(datagrid: Datagrid): void; + initSortableTree(datagrid: Datagrid): void; +} + +export interface Selectpicker { + initSelectpickers(elements: HTMLElement[], datagrid: Datagrid): void; +} + +export interface Datepicker { + initDatepickers(elements: HTMLInputElement[], datagrid: Datagrid): void; +} diff --git a/assets/datagrid/utils.ts b/assets/datagrid/utils.ts new file mode 100644 index 0000000..a4c3b98 --- /dev/null +++ b/assets/datagrid/utils.ts @@ -0,0 +1,180 @@ +import { Datagrid } from "@datagrid/datagrid"; +import { ExtendedWindow } from "@datagrid/types"; + +export function isPromise(p: any): p is Promise { + return typeof p === "object" && typeof p.then === "function"; +} + +export function isInKeyRange(e: KeyboardEvent, min: number, max: number): boolean { + const code = e.key.length === 1 ? e.key.charCodeAt(0) : 0; + return code >= min && code <= max; +} + +export function isEnter(e: KeyboardEvent): boolean { + return e.key === "Enter"; +} + +export function isEsc(e: KeyboardEvent): boolean { + return e.key === "Escape"; +} + +export function isFunctionKey(e: KeyboardEvent): boolean { + return e.key.length === 2 && e.key.startsWith("F"); +} + +export function window(): ExtendedWindow { + return (window ?? {}) as unknown as ExtendedWindow; +} + +export function slideDown(element: HTMLElement, cb?: (nextStateShown: boolean) => unknown) { + element.style.height = 'auto'; + + let height = element.clientHeight + "px"; + + element.style.height = '0px'; + + setTimeout(function () { + element.style.height = height; + cb?.(true); + }, 0); +} + +export function slideUp(element: HTMLElement, cb?: (nextStateShown: boolean) => unknown) { + element.style.height = '0px'; + + setTimeout( () => { + cb?.(false); + }, 250); // TODO +} + +export function slideToggle(element: HTMLElement, isVisible: boolean, cb?: (nextStateShown: boolean) => unknown) { + console.log("element", element); + if (!isVisible) { + slideDown(element, cb); + } else { + slideUp(element, cb); + } +} + +export function attachSlideToggle(element: HTMLElement, control: HTMLElement, cb?: (nextStateShown: boolean) => unknown) { + if (!control.classList.contains("datagrid--slide-toggle")) { + let sliding = false; + control.classList.add("datagrid--slide-toggle"); + + slideDown(element, cb); + + control.addEventListener('click', () => { + if (sliding) return; + sliding = true; + slideToggle(element, control.classList.contains('is-active'), (active) => { + sliding = false + if (active) { + control.classList.add("is-active"); + } else { + control.classList.remove("is-active"); + } + }); + }); + } +} + +export function qs(params: Record, prefix: string = ""): string { + const encodedParams = []; + + for (const _key in params) { + const value = params[_key]; + // Cannot do !value as that would also exclude valid negative values such as 0 or false + if (value === null || value === undefined) continue; + + const key = prefix ? `${prefix}[${_key}]` : _key; + + // Skip empty strings + if (typeof value === "string" && value.trim().length < 1) continue; + + if (typeof value === "object") { + const nestedParams = qs(value, key); + // Don't include if object is empty + if (nestedParams.length >= 1) { + encodedParams.push(nestedParams); + } + + continue; + } + + encodedParams.push(`${encodeURIComponent(key)}=${encodeURIComponent(value)}`) + } + + return encodedParams.join("&").replace(/&+$/gm, "").replace(/&*$/, ""); +} + +export function calculateCellLines(el: HTMLElement) { + const cellPadding = el.style.padding ? parseInt(el.style.padding.replace(/[^-\d\.]/g, ""), 10) : 0; + const cellHeight = el.getBoundingClientRect().height; + const lineHeight = Math.round(parseFloat(el.style.lineHeight ?? "0")); + const cellLines = Math.round((cellHeight - 2 * cellPadding) / lineHeight); + + return cellLines; +} + +// A little better debounce ;) +export function debounce unknown | Promise>( + fn: TFun, + slowdown: number = 200 +): (...args: TArgs[]) => void { + let timeout: number | null = null; + let blockedByPromise: boolean = false; + + return (...args) => { + if (blockedByPromise) return; + + timeout && clearTimeout(timeout); + timeout = setTimeout(() => { + const result = fn(...args); + + if (isPromise(result)) { + blockedByPromise = true; + result.finally(() => { + blockedByPromise = false; + }); + } + }, slowdown); + }; +} + +export function defaultDatagridNameResolver(this: Datagrid, datagrid: HTMLElement) { + // This attribute is not present by default, though if you're going to use this library + // it's recommended to add it, because when not present, the fallback way is to parse the datagrid- class, + // which is definitely far from reliable. Alternatively (mainly in case of a custom datagrid class), + // you can pass your own resolveDatagridName function to the option. + const attrName = datagrid.getAttribute("data-datagrid-name"); + if (attrName) return attrName; + + console.warn( + "Deprecated name resolution for datagrid", + datagrid, + ": Please add a data-datagrid-name attribute instead!\n" + + "Currently, the Datagrid library relies on matching the name from the 'datagrid-[name]' class, which is unreliable " + + "and may cause bugs if the default class names are not used (eg. if you add a datagrid-xx class, or change the name class completely!)\n" + + "Alternatively, you can customize the name resolution with the `resolveDatagridName` option. See TBD for more info." // TODO + ); + + const classes = datagrid.classList.value.split(" "); + + // Returns the first datagrid-XXX match + for (const className of classes) { + if (!className.startsWith("datagrid-")) continue; + + const [, ...split] = className.split("-"); + const name = split.join("-"); + + // In case nothing actually follows the prefix (className = "datagrid-") + if (name.length < 1) { + console.error(`Failed to resolve datagrid name - ambigious class name '${className}'`); + return null; + } + + return name; + } + + return null; +} diff --git a/assets/js/datagrid/datagrid.js b/assets/js/datagrid/datagrid.js deleted file mode 100644 index 29a5206..0000000 --- a/assets/js/datagrid/datagrid.js +++ /dev/null @@ -1,922 +0,0 @@ -var dataGridRegisterExtension, dataGridRegisterAjaxCall, dataGridLoad, dataGridSubmitForm; - -if (typeof naja !== "undefined") { - var isNaja2 = function () { return naja && naja.VERSION && naja.VERSION >= 2 }; - var najaEventParams = function (params) { return isNaja2() ? params.detail : params }; - var najaRequest = function (params) { return isNaja2() ? params.detail.request : params.xhr }; - dataGridRegisterExtension = function (name, extension) { - var init = extension.init; - var success = extension.success; - var before = extension.before; - var complete = extension.complete; - var interaction = extension.interaction; - - - var NewExtension = function NewExtension(naja, name) { - this.name = name; - - this.initialize = function (naja) { - if(init) { - naja.addEventListener('init', function (params) { - init(najaEventParams(params).defaultOptions); - }); - } - - if(success) { - naja.addEventListener('success', function (params) { - var payload = isNaja2() ? params.detail.payload : params.response; - success(payload, najaEventParams(params).options); - }); - } - - var interactionTarget = naja; - if (isNaja2()) { - interactionTarget = interactionTarget.uiHandler; - } - - interactionTarget.addEventListener('interaction', function (params) { - if (isNaja2()) { - params.detail.options.nette = { - el: $(params.detail.element) - } - } else { - params.options.nette = { - el: $(params.element) - } - } - if (interaction) { - if (!interaction(najaEventParams(params).options)){ - params.preventDefault(); - } - } - }); - - if(before) { - naja.addEventListener('before', function (params) { - if (!before(najaRequest(params), najaEventParams(params).options)) - params.preventDefault(); - }); - } - - if(complete) { - naja.addEventListener('complete', function (params) { - complete(najaRequest(params), najaEventParams(params).options); - }); - } - } - if (!isNaja2()) { - this.initialize(naja); - } - return this; - } - - if (isNaja2()) { - naja.registerExtension(new NewExtension(null, name)); - } else { - naja.registerExtension(NewExtension, name); - } - }; - - - dataGridRegisterAjaxCall = function (params) { - var method = params.type || 'GET'; - var data = params.data || null; - - naja.makeRequest(method, params.url, data, {}) - .then(params.success) - .catch(params.error); - }; - - dataGridLoad = function () { - naja.load(); - }; - - dataGridSubmitForm = function (form) { - return naja.uiHandler.submitForm(form.get(0)); - }; -} else if ($.nette) { - dataGridRegisterExtension = function (name, extension) { - $.nette.ext(name, extension); - }; - dataGridRegisterAjaxCall = function (params) { - $.nette.ajax(params); - }; - dataGridLoad = function () { - $.nette.load(); - }; - dataGridSubmitForm = function (form) { - return form.submit(); - }; -} else { - throw new Error("Include Naja.js or nette.ajax for datagrids to work!") -} - - -var datagridFilterMultiSelect, datagridGroupActionMultiSelect, datagridShiftGroupSelection, datagridSortable, datagridSortableTree, getEventDomPath, - indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (i in this && this[i] === item) return i; } return -1; }; - -$(document).on('click', '[data-datagrid-confirm]:not(.ajax)', function(e) { - if (!confirm($(e.target).closest('a').attr('data-datagrid-confirm'))) { - e.stopPropagation(); - return e.preventDefault(); - } -}); - -if (typeof naja !== "undefined") { - dataGridRegisterExtension('datagrid.confirm', { - interaction: function(settings) { - var confirm_message; - if (settings.nette) { - confirm_message = settings.nette.el.data('datagrid-confirm'); - if (confirm_message) { - return confirm(confirm_message); - } - } - return true; - } - }); -} else { - dataGridRegisterExtension('datagrid.confirm', { - before: function(xhr, settings) { - var confirm_message; - if (settings.nette) { - confirm_message = settings.nette.el.data('datagrid-confirm'); - if (confirm_message) { - return confirm(confirm_message); - } - } - return true; - } - }); -} - - -$(document).on('change', 'select[data-autosubmit-per-page]', function() { - var button; - button = $(this).parent().find('input[type=submit]'); - if (button.length === 0) { - button = $(this).parent().find('button[type=submit]'); - } - return button.click(); -}).on('change', 'select[data-autosubmit]', function() { - return dataGridSubmitForm($(this).closest('form').first()); -}).on('change', 'input[data-autosubmit][data-autosubmit-change]', function(e) { - var $this, code; - code = e.which || e.keyCode || 0; - clearTimeout(window.datagrid_autosubmit_timer); - $this = $(this); - return window.datagrid_autosubmit_timer = setTimeout((function(_this) { - return function() { - return dataGridSubmitForm($this.closest('form').first()); - }; - })(this), 200); -}).on('keyup', 'input[data-autosubmit]', function(e) { - var $this, code; - code = e.which || e.keyCode || 0; - if ((code !== 13) && ((code >= 9 && code <= 40) || (code >= 112 && code <= 123))) { - return; - } - clearTimeout(window.datagrid_autosubmit_timer); - $this = $(this); - return window.datagrid_autosubmit_timer = setTimeout((function(_this) { - return function() { - return dataGridSubmitForm($this.closest('form').first()); - }; - })(this), 200); -}).on('keydown', '.datagrid-inline-edit input', function(e) { - var code; - code = e.which || e.keyCode || 0; - if (code === 13) { - e.stopPropagation(); - e.preventDefault(); - return $(this).closest('tr').find('.col-action-inline-edit [name="inline_edit[submit]"]').click(); - } -}); - -$(document).on('keydown', 'input[data-datagrid-manualsubmit]', function(e) { - var code; - code = e.which || e.keyCode || 0; - if (code === 13) { - e.stopPropagation(); - e.preventDefault(); - return dataGridSubmitForm($(this).closest('form').first()); - } -}); - -getEventDomPath = function(e) { - var node, path; - if (indexOf.call(e, path) >= 0) { - return e.path; - } - path = []; - node = e.target; - while (node !== document.body) { - if (node === null) { - break; - } - path.push(node); - node = node.parentNode; - } - return path; -}; - -datagridShiftGroupSelection = function() { - var last_checkbox; - last_checkbox = null; - return document.addEventListener('click', function(e) { - var checkboxes_rows, current_checkbox_row, el, event, i, ie, input, j, k, last_checkbox_row, last_checkbox_tbody, len, len1, len2, ref, ref1, results, row, rows; - ref = getEventDomPath(e); - for (i = 0, len = ref.length; i < len; i++) { - el = ref[i]; - if ($(el).is('.col-checkbox') && last_checkbox && e.shiftKey) { - current_checkbox_row = $(el).closest('tr'); - last_checkbox_row = last_checkbox.closest('tr'); - last_checkbox_tbody = last_checkbox_row.closest('tbody'); - checkboxes_rows = last_checkbox_tbody.find('tr').toArray(); - if (current_checkbox_row.index() > last_checkbox_row.index()) { - rows = checkboxes_rows.slice(last_checkbox_row.index(), current_checkbox_row.index()); - } else if (current_checkbox_row.index() < last_checkbox_row.index()) { - rows = checkboxes_rows.slice(current_checkbox_row.index() + 1, last_checkbox_row.index()); - } - if (!rows) { - return; - } - for (j = 0, len1 = rows.length; j < len1; j++) { - row = rows[j]; - input = $(row).find('.col-checkbox input[type=checkbox]')[0]; - if (input) { - input.checked = true; - ie = window.navigator.userAgent.indexOf("MSIE "); - if (ie) { - event = document.createEvent('Event'); - event.initEvent('change', true, true); - } else { - event = new Event('change', { - 'bubbles': true - }); - } - input.dispatchEvent(event); - } - } - } - } - ref1 = getEventDomPath(e); - results = []; - for (k = 0, len2 = ref1.length; k < len2; k++) { - el = ref1[k]; - if ($(el).is('.col-checkbox')) { - results.push(last_checkbox = $(el)); - } else { - results.push(void 0); - } - } - return results; - }); -}; - -datagridShiftGroupSelection(); - -document.addEventListener('change', function(e) { - var buttons, checked_inputs, counter, event, grid, i, ie, input, inputs, len, results, select, total; - grid = e.target.getAttribute('data-check'); - if (grid) { - checked_inputs = document.querySelectorAll('input[data-check-all-' + grid + ']:checked'); - select = document.querySelector('.datagrid-' + grid + ' select[name="group_action[group_action]"]'); - buttons = document.querySelectorAll('.datagrid-' + grid + ' .row-group-actions *[type="submit"]'); - counter = document.querySelector('.datagrid-' + grid + ' .datagrid-selected-rows-count'); - - if (checked_inputs.length) { - if (buttons) { - buttons.forEach(function (button) { - button.disabled = false; - }); - } - if (select) { - select.disabled = false; - } - total = document.querySelectorAll('input[data-check-all-' + grid + ']').length; - if (counter) { - counter.innerHTML = checked_inputs.length + '/' + total; - } - } else { - if (buttons) { - buttons.forEach(function (button) { - button.disabled = true; - }); - } - if (select) { - select.disabled = true; - select.value = ""; - } - if (counter) { - counter.innerHTML = ""; - } - } - ie = window.navigator.userAgent.indexOf("MSIE "); - if (ie) { - event = document.createEvent('Event'); - event.initEvent('change', true, true); - } else { - event = new Event('change', { - 'bubbles': true - }); - } - if (select) { - select.dispatchEvent(event); - } - } - grid = e.target.getAttribute('data-check-all'); - if (grid) { - inputs = document.querySelectorAll('input[type=checkbox][data-check-all-' + grid + ']'); - results = []; - for (i = 0, len = inputs.length; i < len; i++) { - input = inputs[i]; - input.checked = e.target.checked; - ie = window.navigator.userAgent.indexOf("MSIE "); - if (ie) { - event = document.createEvent('Event'); - event.initEvent('change', true, true); - } else { - event = new Event('change', { - 'bubbles': true - }); - } - results.push(input.dispatchEvent(event)); - } - return results; - } -}); - - -window.datagridSerializeUrl = function(obj, prefix) { - var str = []; - for(var p in obj) { - if (obj.hasOwnProperty(p)) { - var k = prefix ? prefix + "[" + p + "]" : p, v = obj[p]; - if (v !== null && v !== "") { - if (typeof v == "object") { - var r = window.datagridSerializeUrl(v, k); - if (r) { - str.push(r); - } - } else { - str.push(encodeURIComponent(k) + "=" + encodeURIComponent(v)); - } - } - } - } - return str.join("&"); -} -; - -datagridSortable = function() { - if (typeof $.fn.sortable === 'undefined') { - return; - } - return $('.datagrid [data-sortable]').sortable({ - handle: '.handle-sort', - items: 'tr', - axis: 'y', - update: function(event, ui) { - var component_prefix, data, item_id, next_id, prev_id, row, url; - row = ui.item.closest('tr[data-id]'); - item_id = row.data('id'); - prev_id = null; - next_id = null; - if (row.prev().length) { - prev_id = row.prev().data('id'); - } - if (row.next().length) { - next_id = row.next().data('id'); - } - url = $(this).data('sortable-url'); - data = {}; - component_prefix = row.closest('.datagrid').find('tbody').attr('data-sortable-parent-path'); - data[(component_prefix + '-item_id').replace(/^-/, '')] = item_id; - if (prev_id !== null) { - data[(component_prefix + '-prev_id').replace(/^-/, '')] = prev_id; - } - if (next_id !== null) { - data[(component_prefix + '-next_id').replace(/^-/, '')] = next_id; - } - return dataGridRegisterAjaxCall({ - type: 'GET', - url: url, - data: data, - error: function(jqXHR, textStatus, errorThrown) { - return alert(jqXHR.statusText); - } - }); - }, - helper: function(e, ui) { - ui.children().each(function() { - return $(this).width($(this).width()); - }); - return ui; - } - }); -}; - -$(function() { - return datagridSortable(); -}); - -if (typeof datagridSortableTree === 'undefined') { - datagridSortableTree = function() { - if (typeof $('.datagrid-tree-item-children').sortable === 'undefined') { - return; - } - return $('.datagrid-tree-item-children').sortable({ - handle: '.handle-sort', - items: '.datagrid-tree-item:not(.datagrid-tree-header)', - toleranceElement: '> .datagrid-tree-item-content', - connectWith: '.datagrid-tree-item-children', - update: function(event, ui) { - var component_prefix, data, item_id, next_id, parent, parent_id, prev_id, row, url; - $('.toggle-tree-to-delete').remove(); - row = ui.item.closest('.datagrid-tree-item[data-id]'); - item_id = row.data('id'); - prev_id = null; - next_id = null; - parent_id = null; - if (row.prev().length) { - prev_id = row.prev().data('id'); - } - if (row.next().length) { - next_id = row.next().data('id'); - } - parent = row.parent().closest('.datagrid-tree-item'); - if (parent.length) { - parent.find('.datagrid-tree-item-children').first().css({ - display: 'block' - }); - parent.addClass('has-children'); - parent_id = parent.data('id'); - } - url = $(this).data('sortable-url'); - if (!url) { - return; - } - parent.find('[data-toggle-tree]').first().removeClass('hidden'); - component_prefix = row.closest('.datagrid-tree').attr('data-sortable-parent-path'); - data = {}; - data[(component_prefix + '-item_id').replace(/^-/, '')] = item_id; - if (prev_id !== null) { - data[(component_prefix + '-prev_id').replace(/^-/, '')] = prev_id; - } - if (next_id !== null) { - data[(component_prefix + '-next_id').replace(/^-/, '')] = next_id; - } - data[(component_prefix + '-parent_id').replace(/^-/, '')] = parent_id; - return dataGridRegisterAjaxCall({ - type: 'GET', - url: url, - data: data, - error: function(jqXHR, textStatus, errorThrown) { - if (errorThrown !== 'abort') { - return alert(jqXHR.statusText); - } - } - }); - }, - stop: function(event, ui) { - return $('.toggle-tree-to-delete').removeClass('toggle-tree-to-delete'); - }, - start: function(event, ui) { - var parent; - parent = ui.item.parent().closest('.datagrid-tree-item'); - if (parent.length) { - if (parent.find('.datagrid-tree-item').length === 2) { - return parent.find('[data-toggle-tree]').addClass('toggle-tree-to-delete'); - } - } - } - }); - }; -} - -$(function() { - return datagridSortableTree(); -}); - -dataGridRegisterExtension('datagrid.happy', { - success: function() { - var c, checked_rows, class_selector, classes, event, grid, grids, i, ie, input, j, len, len1, results; - if (window.happy) { - window.happy.reset(); - } - grids = $('.datagrid'); - results = []; - for (i = 0, len = grids.length; i < len; i++) { - grid = grids[i]; - classes = grid.classList; - class_selector = ''; - for (j = 0, len1 = classes.length; j < len1; j++) { - c = classes[j]; - class_selector = class_selector + '.' + c; - } - checked_rows = document.querySelectorAll(class_selector + ' ' + 'input[data-check]:checked'); - if (checked_rows.length === 1 && checked_rows[0].getAttribute('name') === 'toggle-all') { - input = document.querySelector(class_selector + ' input[name=toggle-all]'); - if (input) { - input.checked = false; - ie = window.navigator.userAgent.indexOf("MSIE "); - if (ie) { - event = document.createEvent('Event'); - event.initEvent('change', true, true); - } else { - event = new Event('change', { - 'bubbles': true - }); - } - results.push(input.dispatchEvent(event)); - } else { - results.push(void 0); - } - } else { - results.push(void 0); - } - } - return results; - } -}); - -dataGridRegisterExtension('datagrid.sortable', { - success: function() { - return datagridSortable(); - } -}); - -dataGridRegisterExtension('datagrid.forms', { - success: function() { - return $('.datagrid').find('form').each(function() { - return window.Nette.initForm(this); - }); - } -}); - -dataGridRegisterExtension('datagrid.url', { - success: function(payload) { - var host, path, query, url; - if (payload._datagrid_url) { - if (window.history.replaceState) { - host = window.location.protocol + "//" + window.location.host; - path = window.location.pathname; - query = window.datagridSerializeUrl(payload.state).replace(/&+$/gm, ''); - if (query) { - url = host + path + "?" + query.replace(/\&*$/, ''); - } else { - url = host + path; - } - url += window.location.hash; - if (window.location.href !== url) { - return window.history.replaceState({ - path: url - }, '', url); - } - } - } - } -}); - -dataGridRegisterExtension('datagrid.sort', { - success: function(payload) { - var href, key, ref, results; - if (payload._datagrid_sort) { - ref = payload._datagrid_sort; - results = []; - for (key in ref) { - href = ref[key]; - results.push($('#datagrid-sort-' + key).attr('href', href)); - } - return results; - } - } -}); - -dataGridRegisterExtension('datargid.item_detail', { - before: function(xhr, settings) { - var id, row_detail, grid_fullname; - if (settings.nette && settings.nette.el.attr('data-toggle-detail')) { - id = settings.nette.el.attr('data-toggle-detail'); - grid_fullname = settings.nette.el.attr('data-toggle-detail-grid-fullname'); - row_detail = $('.item-detail-' + grid_fullname + '-id-' + id); - if (row_detail.hasClass('loaded')) { - if (!row_detail.find('.item-detail-content').length) { - row_detail.removeClass('toggled'); - return true; - } - if (row_detail.hasClass('toggled')) { - row_detail.find('.item-detail-content').slideToggle('fast', (function(_this) { - return function() { - return row_detail.toggleClass('toggled'); - }; - })(this)); - } else { - row_detail.toggleClass('toggled'); - row_detail.find('.item-detail-content').slideToggle('fast'); - } - return false; - } else { - return row_detail.addClass('loaded'); - } - } - return true; - }, - success: function(payload) { - var id, row_detail, grid_fullname; - if (payload._datagrid_toggle_detail && payload._datagrid_name) { - id = payload._datagrid_toggle_detail; - grid_fullname = payload._datagrid_name; - row_detail = $('.item-detail-' + grid_fullname + '-id-' + id); - row_detail.toggleClass('toggled'); - return row_detail.find('.item-detail-content').slideToggle('fast'); - } - } -}); - -dataGridRegisterExtension('datagrid.tree', { - before: function(xhr, settings) { - var children_block; - if (settings.nette && settings.nette.el.attr('data-toggle-tree')) { - settings.nette.el.toggleClass('toggle-rotate'); - children_block = settings.nette.el.closest('.datagrid-tree-item').find('.datagrid-tree-item-children').first(); - if (children_block.hasClass('loaded')) { - children_block.slideToggle('fast'); - return false; - } - } - return true; - }, - success: function(payload) { - var children_block, content, id, name, ref, snippet, template; - if (payload._datagrid_tree) { - id = payload._datagrid_tree; - children_block = $('.datagrid-tree-item[data-id="' + id + '"]').find('.datagrid-tree-item-children').first(); - children_block.addClass('loaded'); - ref = payload.snippets; - for (name in ref) { - snippet = ref[name]; - content = $(snippet); - template = $('

'); - template.attr('data-id', content.attr('data-id')); - template.append(content); - if (content.data('has-children')) { - template.addClass('has-children'); - } - children_block.append(template); - } - children_block.addClass('loaded'); - children_block.slideToggle('fast'); - dataGridLoad(); - } - return datagridSortableTree(); - } -}); - -$(document).on('click', '[data-datagrid-editable-url]', function(event) { - var attr_name, attr_value, attrs, cell, cellValue, cell_height, cell_lines, cell_padding, input, line_height, submit, valueToEdit; - cell = $(this); - if (event.target.tagName.toLowerCase() === 'a') { - return; - } - if (cell.hasClass('datagrid-inline-edit')) { - return; - } - if (!cell.hasClass('editing')) { - cell.addClass('editing'); - cellValue = cell.html().trim().replace('
', '\n'); - if (cell.attr('data-datagrid-editable-value')) { - valueToEdit = String(cell.data('datagrid-editable-value')); - } else { - valueToEdit = cellValue; - } - cell.data('originalValue', cellValue); - cell.data('valueToEdit', valueToEdit); - if (cell.data('datagrid-editable-type') === 'textarea') { - input = $(''); - cell_padding = parseInt(cell.css('padding').replace(/[^-\d\.]/g, ''), 10); - cell_height = cell.outerHeight(); - line_height = Math.round(parseFloat(cell.css('line-height'))); - cell_lines = (cell_height - (2 * cell_padding)) / line_height; - input.attr('rows', Math.round(cell_lines)); - } else if (cell.data('datagrid-editable-type') === 'select') { - input = $(cell.data('datagrid-editable-element')); - input.find("option[value='" + valueToEdit + "']").prop('selected', true); - } else { - input = $(''); - input.val(valueToEdit); - } - attrs = cell.data('datagrid-editable-attrs'); - for (attr_name in attrs) { - attr_value = attrs[attr_name]; - input.attr(attr_name, attr_value); - } - cell.removeClass('edited'); - cell.html(input); - submit = function(cell, el) { - var value; - value = el.val(); - if (value !== cell.data('valueToEdit')) { - dataGridRegisterAjaxCall({ - url: cell.data('datagrid-editable-url'), - data: { - value: value - }, - type: 'POST', - success: function(payload) { - if (cell.data('datagrid-editable-type') === 'select') { - cell.html(input.find("option[value='" + value + "']").html()); - } else { - if (payload._datagrid_editable_new_value) { - value = payload._datagrid_editable_new_value; - } - cell.html(value); - } - return cell.addClass('edited'); - }, - error: function() { - cell.html(cell.data('originalValue')); - return cell.addClass('edited-error'); - } - }); - } else { - cell.html(cell.data('originalValue')); - } - return setTimeout(function() { - return cell.removeClass('editing'); - }, 1200); - }; - cell.find('input,textarea,select').focus().on('blur', function() { - return submit(cell, $(this)); - }).on('keydown', function(e) { - if (cell.data('datagrid-editable-type') !== 'textarea') { - if (e.which === 13) { - e.stopPropagation(); - e.preventDefault(); - return submit(cell, $(this)); - } - } - if (e.which === 27) { - e.stopPropagation(); - e.preventDefault(); - cell.removeClass('editing'); - return cell.html(cell.data('originalValue')); - } - }); - return cell.find('select').on('change', function() { - return submit(cell, $(this)); - }); - } -}); - -dataGridRegisterExtension('datagrid.after_inline_edit', { - success: function(payload) { - var grid = $('.datagrid-' + payload._datagrid_name); - - if (payload._datagrid_inline_edited) { - grid.find('tr[data-id="' + payload._datagrid_inline_edited + '"] > td').addClass('edited'); - return grid.find('.datagrid-inline-edit-trigger').removeClass('hidden'); - } else if (payload._datagrid_inline_edit_cancel) { - return grid.find('.datagrid-inline-edit-trigger').removeClass('hidden'); - } - } -}); - -$(document).on('mouseup', '[data-datagrid-cancel-inline-add]', function(e) { - var code = e.which || e.keyCode || 0; - if (code === 1) { - e.stopPropagation(); - e.preventDefault(); - return $('.datagrid-row-inline-add').addClass('datagrid-row-inline-add-hidden'); - } -}); - -dataGridRegisterExtension('datagrid-toggle-inline-add', { - success: function(payload) { - var grid = $('.datagrid-' + payload._datagrid_name); - - if (payload._datagrid_inline_adding) { - var row = grid.find('.datagrid-row-inline-add'); - - if (row.hasClass('datagrid-row-inline-add-hidden')) { - row.removeClass('datagrid-row-inline-add-hidden'); - } - - row.find('input:not([readonly]),textarea:not([readonly])').first().focus(); - } - } -}); - -datagridFilterMultiSelect = function() { - var select = $('.selectpicker').first(); - - if ($.fn.selectpicker) { - let defaults = $.fn.selectpicker.defaults = { - countSelectedText: select.data('i18n-selected'), - iconBase: '', - tickIcon: select.data('selected-icon-check') - }; - - $('.selectpicker') - .removeClass('form-select form-select-sm') - .addClass('form-control form-control-sm') - .selectpicker('destroy') - .selectpicker({ - iconBase: 'fa' - }); - - return defaults; - } -}; - -$(function() { - return datagridFilterMultiSelect(); -}); - -datagridGroupActionMultiSelect = function() { - var selects; - - if (!$.fn.selectpicker) { - return; - } - - selects = $('[data-datagrid-multiselect-id]'); - - return selects.each(function() { - var id; - if ($(this).hasClass('selectpicker')) { - $(this).removeAttr('id'); - id = $(this).data('datagrid-multiselect-id'); - $(this).on('loaded.bs.select', function(e) { - $(this).parent().attr('style', 'display:none;'); - return $(this).parent().find('.hidden').removeClass('hidden').addClass('btn-default btn-secondary'); - }); - return $(this).on('rendered.bs.select', function(e) { - return $(this).parent().attr('id', id); - }); - } - }); -}; - -$(function() { - return datagridGroupActionMultiSelect(); -}); - -dataGridRegisterExtension('datagrid.fitlerMultiSelect', { - success: function() { - datagridFilterMultiSelect(); - } -}); - -dataGridRegisterExtension('datagrid.groupActionMultiSelect', { - success: function() { - return datagridGroupActionMultiSelect(); - } -}); - -dataGridRegisterExtension('datagrid.inline-editing', { - success: function(payload) { - var grid; - if (payload._datagrid_inline_editing) { - grid = $('.datagrid-' + payload._datagrid_name); - return grid.find('.datagrid-inline-edit-trigger').addClass('hidden'); - } - } -}); - -dataGridRegisterExtension('datagrid.redraw-item', { - success: function(payload) { - var row; - if (payload._datagrid_redraw_item_class) { - row = $('tr[data-id="' + payload._datagrid_redraw_item_id + '"]'); - return row.attr('class', payload._datagrid_redraw_item_class); - } - } -}); - -dataGridRegisterExtension('datagrid.reset-filter-by-column', { - success: function(payload) { - var grid, href, i, key, len, ref; - if (!payload._datagrid_name) { - return; - } - grid = $('.datagrid-' + payload._datagrid_name); - grid.find('[data-datagrid-reset-filter-by-column]').addClass('hidden'); - if (payload.non_empty_filters && payload.non_empty_filters.length) { - ref = payload.non_empty_filters; - for (i = 0, len = ref.length; i < len; i++) { - key = ref[i]; - grid.find('[data-datagrid-reset-filter-by-column="' + key + '"]').removeClass('hidden'); - } - href = grid.find('.reset-filter').attr('href'); - return grid.find('[data-datagrid-reset-filter-by-column]').each(function() { - var new_href; - key = $(this).attr('data-datagrid-reset-filter-by-column'); - new_href = href.replace('do=' + payload._datagrid_name + '-resetFilter', 'do=' + payload._datagrid_name + '-resetColumnFilter'); - new_href += '&' + payload._datagrid_name + '-key=' + key; - return $(this).attr('href', new_href); - }); - } - } -}); diff --git a/assets/js/datagrid/instant-url-refresh.js b/assets/js/datagrid/instant-url-refresh.js deleted file mode 100644 index d0caef0..0000000 --- a/assets/js/datagrid/instant-url-refresh.js +++ /dev/null @@ -1,30 +0,0 @@ -var dataGridRegisterAjaxCall; - -if (typeof naja !== "undefined") { - dataGridRegisterAjaxCall = function (params) { - var method = params.type || 'GET'; - var data = params.data || null; - - naja.makeRequest(method, params.url, data, { - history: 'replace' - }) - .then(params.success) - .catch(params.error); - }; - -} else { - dataGridRegisterAjaxCall = function (params) { - $.nette.ajax(params); - }; -} - -document.addEventListener('DOMContentLoaded', function () { - var element = document.querySelector('.datagrid'); - - if (element !== null) { - return dataGridRegisterAjaxCall({ - type: 'GET', - url: element.getAttribute('data-refresh-state') - }); - } -}); diff --git a/assets/js/datagrid/spinners.js b/assets/js/datagrid/spinners.js deleted file mode 100644 index a680ba3..0000000 --- a/assets/js/datagrid/spinners.js +++ /dev/null @@ -1,89 +0,0 @@ -var dataGridRegisterExtension; - -if (typeof naja !== "undefined") { - var isNaja2 = function () { return naja && naja.VERSION && naja.VERSION >= 2 }; - var najaEventParams = function (params) { return isNaja2() ? params.detail : params }; - var najaRequest = function (params) { return isNaja2() ? params.detail.request : params.xhr }; - dataGridRegisterExtension = function (name, extension) { - var init = extension.init; - var success = extension.success; - var before = extension.before; - var complete = extension.complete; - - - var NewExtension = function NewExtension(naja, name) { - this.name = name; - - this.initialize = function (naja) { - if(init) { - naja.addEventListener('init', function (params) { - init(najaEventParams(params).defaultOptions); - }); - } - - if(success) { - naja.addEventListener('success', function (params) { - var payload = isNaja2() ? params.detail.payload : params.response; - success(payload, najaEventParams(params).options); - }); - } - - if(before) { - naja.addEventListener('before', function (params) { - before(najaRequest(params), najaEventParams(params).options); - }); - } - - if(complete) { - naja.addEventListener('complete', function (params) { - complete(najaRequest(params), najaEventParams(params).options); - }); - } - } - if (!isNaja2()) { - this.initialize(naja); - } - return this; - } - - if (isNaja2()) { - naja.registerExtension(new NewExtension(null, name)); - } else { - naja.registerExtension(NewExtension, name); - } - }; -} else if ($.nette) { - dataGridRegisterExtension = function (name, extension) { - $.nette.ext(name, extension); - }; -} - -dataGridRegisterExtension('ublaboo-spinners', { - before: function(xhr, settings) { - var el, id, row_detail, spinner_template, grid_fullname; - if (settings.nette) { - el = settings.nette.el; - spinner_template = $('
'); - if (el.is('.datagrid [name="group_action[submit]"]')) { - return el.after(spinner_template); - } else if (el.is('.datagrid a') && el.data('toggle-detail')) { - id = settings.nette.el.attr('data-toggle-detail'); - grid_fullname = settings.nette.el.attr('data-toggle-detail-grid-fullname'); - row_detail = $('.item-detail-' + grid_fullname + '-id-' + id); - if (!row_detail.hasClass('loaded')) { - return el.addClass('ublaboo-spinner-icon'); - } - } else if (el.is('.datagrid .col-pagination a')) { - return el.closest('.row-grid-bottom').find('.col-per-page').prepend(spinner_template); - } else if (el.is('.datagrid .datagrid-per-page-submit')) { - return el.closest('.row-grid-bottom').find('.col-per-page').prepend(spinner_template); - } else if (el.is('.datagrid .reset-filter')) { - return el.closest('.row-grid-bottom').find('.col-per-page').prepend(spinner_template); - } - } - }, - complete: function() { - $('.ublaboo-spinner').remove(); - return $('.ublaboo-spinner-icon').removeClass('ublaboo-spinner-icon'); - } -}); diff --git a/assets/js/main.js b/assets/js/main.js index be1ed92..965a642 100644 --- a/assets/js/main.js +++ b/assets/js/main.js @@ -1,8 +1,25 @@ -// import 'ublaboo-datagrid/assets/datagrid.js'; -// import 'ublaboo-datagrid/assets/datagrid-spinners.js'; -// import 'ublaboo-datagrid/assets/datagrid-instant-url-refresh.js'; import naja from "naja"; import netteForms from "nette-forms"; +import { + AutosubmitPlugin, + BootstrapSelect, + CheckboxPlugin, + ConfirmPlugin, + createDatagrids, + Happy, + HappyPlugin, + InlinePlugin, + NetteFormsPlugin, + SelectpickerPlugin, + DatepickerPlugin, + SortableJS, + SortablePlugin, TomSelect, + UrlPlugin, + VanillaDatepicker, ItemDetailPlugin +} from "@datagrid"; +import {NajaAjax} from "@datagrid/ajax"; +import Select from "tom-select"; +import {Dropdown} from "bootstrap"; // Code highlighting import Prism from "prismjs/components/prism-core"; import "prismjs/components/prism-markup-templating"; @@ -11,11 +28,36 @@ import "prismjs/components/prism-clike"; import "prismjs/components/prism-javascript"; import "prismjs/components/prism-css"; // Styles + import '../css/main.css'; +import { TreeViewPlugin } from "../datagrid/plugins/features/treeView"; document.addEventListener("DOMContentLoaded", () => { // AJAX naja.formsHandler.netteForms = netteForms; + + Array.from(document.querySelectorAll('.dropdown')) + .forEach(el => new Dropdown(el)) + + createDatagrids(new NajaAjax(naja), { + datagrid: { + plugins: [ + new AutosubmitPlugin(), + new CheckboxPlugin(), + new ConfirmPlugin(), + new InlinePlugin(), + new ItemDetailPlugin(), + // new UrlPlugin(), + new NetteFormsPlugin(netteForms), + new HappyPlugin(new Happy()), + new SortablePlugin(new SortableJS()), + new DatepickerPlugin(new VanillaDatepicker({buttonClass: 'btn'})), + new SelectpickerPlugin(new TomSelect(Select)), + new TreeViewPlugin(), + ], + }, + }); + naja.initialize(); // Highlighting diff --git a/composer.lock b/composer.lock index ff20027..454ce4f 100644 --- a/composer.lock +++ b/composer.lock @@ -684,16 +684,16 @@ }, { "name": "latte/latte", - "version": "v3.0.5", + "version": "v3.0.6", "source": { "type": "git", "url": "https://github.com/nette/latte.git", - "reference": "1ccb0add4ddc5e8b5db3b82a145fa9ff2d9d6f8f" + "reference": "6f66dcfea7ad76f60b8234139161421e9e1e309f" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/latte/zipball/1ccb0add4ddc5e8b5db3b82a145fa9ff2d9d6f8f", - "reference": "1ccb0add4ddc5e8b5db3b82a145fa9ff2d9d6f8f", + "url": "https://api.github.com/repos/nette/latte/zipball/6f66dcfea7ad76f60b8234139161421e9e1e309f", + "reference": "6f66dcfea7ad76f60b8234139161421e9e1e309f", "shasum": "" }, "require": { @@ -763,9 +763,9 @@ ], "support": { "issues": "https://github.com/nette/latte/issues", - "source": "https://github.com/nette/latte/tree/v3.0.5" + "source": "https://github.com/nette/latte/tree/v3.0.6" }, - "time": "2023-01-16T23:22:36+00:00" + "time": "2023-03-09T01:34:56+00:00" }, { "name": "nette/application", @@ -1004,16 +1004,16 @@ }, { "name": "nette/di", - "version": "v3.1.1", + "version": "v3.1.2", "source": { "type": "git", "url": "https://github.com/nette/di.git", - "reference": "4799ee684453bf5e70df1e87bec80bfbfc0e7d13" + "reference": "355cefbd71011a76b670fda3340d612a6944f972" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/di/zipball/4799ee684453bf5e70df1e87bec80bfbfc0e7d13", - "reference": "4799ee684453bf5e70df1e87bec80bfbfc0e7d13", + "url": "https://api.github.com/repos/nette/di/zipball/355cefbd71011a76b670fda3340d612a6944f972", + "reference": "355cefbd71011a76b670fda3340d612a6944f972", "shasum": "" }, "require": { @@ -1070,9 +1070,9 @@ ], "support": { "issues": "https://github.com/nette/di/issues", - "source": "https://github.com/nette/di/tree/v3.1.1" + "source": "https://github.com/nette/di/tree/v3.1.2" }, - "time": "2023-01-16T03:38:02+00:00" + "time": "2023-03-13T14:03:15+00:00" }, { "name": "nette/finder", @@ -1143,16 +1143,16 @@ }, { "name": "nette/forms", - "version": "v3.1.10", + "version": "v3.1.11", "source": { "type": "git", "url": "https://github.com/nette/forms.git", - "reference": "12b4c12e9d65a4c97e10a37cee88fdd14db780b7" + "reference": "64cdc2d6796a8fe1265bb21a6ee5e9ff93e2b3a4" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/forms/zipball/12b4c12e9d65a4c97e10a37cee88fdd14db780b7", - "reference": "12b4c12e9d65a4c97e10a37cee88fdd14db780b7", + "url": "https://api.github.com/repos/nette/forms/zipball/64cdc2d6796a8fe1265bb21a6ee5e9ff93e2b3a4", + "reference": "64cdc2d6796a8fe1265bb21a6ee5e9ff93e2b3a4", "shasum": "" }, "require": { @@ -1211,22 +1211,22 @@ ], "support": { "issues": "https://github.com/nette/forms/issues", - "source": "https://github.com/nette/forms/tree/v3.1.10" + "source": "https://github.com/nette/forms/tree/v3.1.11" }, - "time": "2023-01-19T14:37:56+00:00" + "time": "2023-03-08T23:56:24+00:00" }, { "name": "nette/http", - "version": "v3.2.1", + "version": "v3.2.2", "source": { "type": "git", "url": "https://github.com/nette/http.git", - "reference": "0e16cd4f911665679b96bf569318a0dc7f087eda" + "reference": "9105c26de3dd47da5e7cf6b4132b5d871f835e25" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/http/zipball/0e16cd4f911665679b96bf569318a0dc7f087eda", - "reference": "0e16cd4f911665679b96bf569318a0dc7f087eda", + "url": "https://api.github.com/repos/nette/http/zipball/9105c26de3dd47da5e7cf6b4132b5d871f835e25", + "reference": "9105c26de3dd47da5e7cf6b4132b5d871f835e25", "shasum": "" }, "require": { @@ -1289,9 +1289,9 @@ ], "support": { "issues": "https://github.com/nette/http/issues", - "source": "https://github.com/nette/http/tree/v3.2.1" + "source": "https://github.com/nette/http/tree/v3.2.2" }, - "time": "2022-12-05T00:03:40+00:00" + "time": "2023-03-18T14:55:56+00:00" }, { "name": "nette/neon", @@ -1363,23 +1363,24 @@ }, { "name": "nette/php-generator", - "version": "v4.0.5", + "version": "v4.0.6", "source": { "type": "git", "url": "https://github.com/nette/php-generator.git", - "reference": "a8d6abeae5d8c7202cd69600e086a7a72877fc86" + "reference": "0f1275bb8d39b3eb92b57c22a51fe693f1f145a5" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/php-generator/zipball/a8d6abeae5d8c7202cd69600e086a7a72877fc86", - "reference": "a8d6abeae5d8c7202cd69600e086a7a72877fc86", + "url": "https://api.github.com/repos/nette/php-generator/zipball/0f1275bb8d39b3eb92b57c22a51fe693f1f145a5", + "reference": "0f1275bb8d39b3eb92b57c22a51fe693f1f145a5", "shasum": "" }, "require": { - "nette/utils": "^3.2.7 || ^4.0", + "nette/utils": "^3.2.9 || ^4.0", "php": ">=8.0 <8.3" }, "require-dev": { + "jetbrains/phpstorm-attributes": "dev-master", "nette/tester": "^2.4", "nikic/php-parser": "^4.15", "phpstan/phpstan": "^1.0", @@ -1425,9 +1426,9 @@ ], "support": { "issues": "https://github.com/nette/php-generator/issues", - "source": "https://github.com/nette/php-generator/tree/v4.0.5" + "source": "https://github.com/nette/php-generator/tree/v4.0.6" }, - "time": "2022-11-02T20:37:46+00:00" + "time": "2023-03-13T17:38:30+00:00" }, { "name": "nette/robot-loader", @@ -2105,16 +2106,16 @@ }, { "name": "symfony/property-access", - "version": "v6.2.7", + "version": "v6.2.8", "source": { "type": "git", "url": "https://github.com/symfony/property-access.git", - "reference": "5a389172011e2c37b47c896d0b156549126690a1" + "reference": "2ad1e0a07b8cab3e09905659d14f3b248e916374" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/property-access/zipball/5a389172011e2c37b47c896d0b156549126690a1", - "reference": "5a389172011e2c37b47c896d0b156549126690a1", + "url": "https://api.github.com/repos/symfony/property-access/zipball/2ad1e0a07b8cab3e09905659d14f3b248e916374", + "reference": "2ad1e0a07b8cab3e09905659d14f3b248e916374", "shasum": "" }, "require": { @@ -2161,11 +2162,11 @@ "injection", "object", "property", - "property path", + "property-path", "reflection" ], "support": { - "source": "https://github.com/symfony/property-access/tree/v6.2.7" + "source": "https://github.com/symfony/property-access/tree/v6.2.8" }, "funding": [ { @@ -2181,20 +2182,20 @@ "type": "tidelift" } ], - "time": "2023-02-14T08:44:56+00:00" + "time": "2023-03-14T15:00:05+00:00" }, { "name": "symfony/property-info", - "version": "v6.2.7", + "version": "v6.2.8", "source": { "type": "git", "url": "https://github.com/symfony/property-info.git", - "reference": "5cf906918ea0f74032ffc5c0b85def246ce409df" + "reference": "400a019b7c05030599fd15f02b3d4ce287631732" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/property-info/zipball/5cf906918ea0f74032ffc5c0b85def246ce409df", - "reference": "5cf906918ea0f74032ffc5c0b85def246ce409df", + "url": "https://api.github.com/repos/symfony/property-info/zipball/400a019b7c05030599fd15f02b3d4ce287631732", + "reference": "400a019b7c05030599fd15f02b3d4ce287631732", "shasum": "" }, "require": { @@ -2254,7 +2255,7 @@ "validator" ], "support": { - "source": "https://github.com/symfony/property-info/tree/v6.2.7" + "source": "https://github.com/symfony/property-info/tree/v6.2.8" }, "funding": [ { @@ -2270,20 +2271,20 @@ "type": "tidelift" } ], - "time": "2023-02-14T08:53:37+00:00" + "time": "2023-03-14T15:00:05+00:00" }, { "name": "symfony/string", - "version": "v6.2.7", + "version": "v6.2.8", "source": { "type": "git", "url": "https://github.com/symfony/string.git", - "reference": "67b8c1eec78296b85dc1c7d9743830160218993d" + "reference": "193e83bbd6617d6b2151c37fff10fa7168ebddef" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/string/zipball/67b8c1eec78296b85dc1c7d9743830160218993d", - "reference": "67b8c1eec78296b85dc1c7d9743830160218993d", + "url": "https://api.github.com/repos/symfony/string/zipball/193e83bbd6617d6b2151c37fff10fa7168ebddef", + "reference": "193e83bbd6617d6b2151c37fff10fa7168ebddef", "shasum": "" }, "require": { @@ -2340,7 +2341,7 @@ "utf8" ], "support": { - "source": "https://github.com/symfony/string/tree/v6.2.7" + "source": "https://github.com/symfony/string/tree/v6.2.8" }, "funding": [ { @@ -2356,26 +2357,26 @@ "type": "tidelift" } ], - "time": "2023-02-24T10:42:00+00:00" + "time": "2023-03-20T16:06:02+00:00" }, { "name": "tracy/tracy", - "version": "v2.9.7", + "version": "v2.10.2", "source": { "type": "git", "url": "https://github.com/nette/tracy.git", - "reference": "1c6e9b5bad030fdf49194154c9674201fa6372bb" + "reference": "882fee7cf4258a602ad4a37461e837ed2ca1406b" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/tracy/zipball/1c6e9b5bad030fdf49194154c9674201fa6372bb", - "reference": "1c6e9b5bad030fdf49194154c9674201fa6372bb", + "url": "https://api.github.com/repos/nette/tracy/zipball/882fee7cf4258a602ad4a37461e837ed2ca1406b", + "reference": "882fee7cf4258a602ad4a37461e837ed2ca1406b", "shasum": "" }, "require": { "ext-json": "*", "ext-session": "*", - "php": ">=7.2 <8.3" + "php": ">=8.0 <8.3" }, "conflict": { "nette/di": "<3.0" @@ -2392,7 +2393,7 @@ "type": "library", "extra": { "branch-alias": { - "dev-master": "2.9-dev" + "dev-master": "2.10-dev" } }, "autoload": { @@ -2428,9 +2429,9 @@ ], "support": { "issues": "https://github.com/nette/tracy/issues", - "source": "https://github.com/nette/tracy/tree/v2.9.7" + "source": "https://github.com/nette/tracy/tree/v2.10.2" }, - "time": "2023-02-28T13:01:54+00:00" + "time": "2023-03-29T12:34:53+00:00" }, { "name": "ublaboo/datagrid", @@ -2438,12 +2439,12 @@ "source": { "type": "git", "url": "https://github.com/contributte/datagrid.git", - "reference": "1aca86dbff52f13bd771ab6f3cbac003b28b605b" + "reference": "d7bbdacb738565bf0adef37059b179c33104fa0f" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/contributte/datagrid/zipball/1aca86dbff52f13bd771ab6f3cbac003b28b605b", - "reference": "1aca86dbff52f13bd771ab6f3cbac003b28b605b", + "url": "https://api.github.com/repos/contributte/datagrid/zipball/d7bbdacb738565bf0adef37059b179c33104fa0f", + "reference": "d7bbdacb738565bf0adef37059b179c33104fa0f", "shasum": "" }, "require": { @@ -2520,7 +2521,7 @@ "type": "github" } ], - "time": "2023-03-07T15:24:33+00:00" + "time": "2023-03-20T09:19:46+00:00" } ], "packages-dev": [ @@ -2530,12 +2531,12 @@ "source": { "type": "git", "url": "https://github.com/contributte/qa.git", - "reference": "8ef95fed5ab32dc7bb2f87bed4c471ac1987a6ac" + "reference": "0565ff342e32f14d6bcdaa961565287ba583fcd7" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/contributte/qa/zipball/8ef95fed5ab32dc7bb2f87bed4c471ac1987a6ac", - "reference": "8ef95fed5ab32dc7bb2f87bed4c471ac1987a6ac", + "url": "https://api.github.com/repos/contributte/qa/zipball/0565ff342e32f14d6bcdaa961565287ba583fcd7", + "reference": "0565ff342e32f14d6bcdaa961565287ba583fcd7", "shasum": "" }, "require": { @@ -2591,7 +2592,7 @@ "type": "github" } ], - "time": "2022-12-22T15:09:44+00:00" + "time": "2023-04-08T12:28:17+00:00" }, { "name": "contributte/tester", @@ -2832,16 +2833,16 @@ }, { "name": "phpstan/phpdoc-parser", - "version": "1.15.3", + "version": "1.18.1", "source": { "type": "git", "url": "https://github.com/phpstan/phpdoc-parser.git", - "reference": "61800f71a5526081d1b5633766aa88341f1ade76" + "reference": "22dcdfd725ddf99583bfe398fc624ad6c5004a0f" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpdoc-parser/zipball/61800f71a5526081d1b5633766aa88341f1ade76", - "reference": "61800f71a5526081d1b5633766aa88341f1ade76", + "url": "https://api.github.com/repos/phpstan/phpdoc-parser/zipball/22dcdfd725ddf99583bfe398fc624ad6c5004a0f", + "reference": "22dcdfd725ddf99583bfe398fc624ad6c5004a0f", "shasum": "" }, "require": { @@ -2871,22 +2872,22 @@ "description": "PHPDoc parser with support for nullable, intersection and generic types", "support": { "issues": "https://github.com/phpstan/phpdoc-parser/issues", - "source": "https://github.com/phpstan/phpdoc-parser/tree/1.15.3" + "source": "https://github.com/phpstan/phpdoc-parser/tree/1.18.1" }, - "time": "2022-12-20T20:56:55+00:00" + "time": "2023-04-07T11:51:11+00:00" }, { "name": "phpstan/phpstan", - "version": "1.10.5", + "version": "1.10.13", "source": { "type": "git", "url": "https://github.com/phpstan/phpstan.git", - "reference": "1fb6f494d82455151ecf15c5c191923f5d84324e" + "reference": "f07bf8c6980b81bf9e49d44bd0caf2e737614a70" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpstan/zipball/1fb6f494d82455151ecf15c5c191923f5d84324e", - "reference": "1fb6f494d82455151ecf15c5c191923f5d84324e", + "url": "https://api.github.com/repos/phpstan/phpstan/zipball/f07bf8c6980b81bf9e49d44bd0caf2e737614a70", + "reference": "f07bf8c6980b81bf9e49d44bd0caf2e737614a70", "shasum": "" }, "require": { @@ -2915,8 +2916,11 @@ "static analysis" ], "support": { + "docs": "https://phpstan.org/user-guide/getting-started", + "forum": "https://github.com/phpstan/phpstan/discussions", "issues": "https://github.com/phpstan/phpstan/issues", - "source": "https://github.com/phpstan/phpstan/tree/1.10.5" + "security": "https://github.com/phpstan/phpstan/security/policy", + "source": "https://github.com/phpstan/phpstan-src" }, "funding": [ { @@ -2932,20 +2936,20 @@ "type": "tidelift" } ], - "time": "2023-03-07T16:48:45+00:00" + "time": "2023-04-12T19:29:52+00:00" }, { "name": "phpstan/phpstan-deprecation-rules", - "version": "1.1.2", + "version": "1.1.3", "source": { "type": "git", "url": "https://github.com/phpstan/phpstan-deprecation-rules.git", - "reference": "bcc1e8cdf81c3da1a2ba9188ee94cd7e2a62e865" + "reference": "a22b36b955a2e9a3d39fe533b6c1bb5359f9c319" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpstan-deprecation-rules/zipball/bcc1e8cdf81c3da1a2ba9188ee94cd7e2a62e865", - "reference": "bcc1e8cdf81c3da1a2ba9188ee94cd7e2a62e865", + "url": "https://api.github.com/repos/phpstan/phpstan-deprecation-rules/zipball/a22b36b955a2e9a3d39fe533b6c1bb5359f9c319", + "reference": "a22b36b955a2e9a3d39fe533b6c1bb5359f9c319", "shasum": "" }, "require": { @@ -2978,9 +2982,9 @@ "description": "PHPStan rules for detecting usage of deprecated classes, methods, properties, constants and traits.", "support": { "issues": "https://github.com/phpstan/phpstan-deprecation-rules/issues", - "source": "https://github.com/phpstan/phpstan-deprecation-rules/tree/1.1.2" + "source": "https://github.com/phpstan/phpstan-deprecation-rules/tree/1.1.3" }, - "time": "2023-01-17T16:14:21+00:00" + "time": "2023-03-17T07:50:08+00:00" }, { "name": "phpstan/phpstan-dibi", @@ -3039,16 +3043,16 @@ }, { "name": "phpstan/phpstan-nette", - "version": "1.2.4", + "version": "1.2.9", "source": { "type": "git", "url": "https://github.com/phpstan/phpstan-nette.git", - "reference": "9e083bb5befde7b73f9a12fc5bd223a7dcd63920" + "reference": "0e3a6805917811d685e59bb83c2286315f2f6d78" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpstan-nette/zipball/9e083bb5befde7b73f9a12fc5bd223a7dcd63920", - "reference": "9e083bb5befde7b73f9a12fc5bd223a7dcd63920", + "url": "https://api.github.com/repos/phpstan/phpstan-nette/zipball/0e3a6805917811d685e59bb83c2286315f2f6d78", + "reference": "0e3a6805917811d685e59bb83c2286315f2f6d78", "shasum": "" }, "require": { @@ -3064,6 +3068,7 @@ "nette/utils": "<2.3.0" }, "require-dev": { + "nette/application": "^3.0", "nette/forms": "^3.0", "nette/utils": "^2.3.0 || ^3.0.0", "nikic/php-parser": "^4.13.2", @@ -3094,22 +3099,22 @@ "description": "Nette Framework class reflection extension for PHPStan", "support": { "issues": "https://github.com/phpstan/phpstan-nette/issues", - "source": "https://github.com/phpstan/phpstan-nette/tree/1.2.4" + "source": "https://github.com/phpstan/phpstan-nette/tree/1.2.9" }, - "time": "2023-02-18T13:39:23+00:00" + "time": "2023-04-12T14:11:53+00:00" }, { "name": "phpstan/phpstan-strict-rules", - "version": "1.5.0", + "version": "1.5.1", "source": { "type": "git", "url": "https://github.com/phpstan/phpstan-strict-rules.git", - "reference": "b7dd96a5503919a43b3cd06a2dced9d4252492f2" + "reference": "b21c03d4f6f3a446e4311155f4be9d65048218e6" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpstan-strict-rules/zipball/b7dd96a5503919a43b3cd06a2dced9d4252492f2", - "reference": "b7dd96a5503919a43b3cd06a2dced9d4252492f2", + "url": "https://api.github.com/repos/phpstan/phpstan-strict-rules/zipball/b21c03d4f6f3a446e4311155f4be9d65048218e6", + "reference": "b21c03d4f6f3a446e4311155f4be9d65048218e6", "shasum": "" }, "require": { @@ -3143,38 +3148,38 @@ "description": "Extra strict and opinionated rules for PHPStan", "support": { "issues": "https://github.com/phpstan/phpstan-strict-rules/issues", - "source": "https://github.com/phpstan/phpstan-strict-rules/tree/1.5.0" + "source": "https://github.com/phpstan/phpstan-strict-rules/tree/1.5.1" }, - "time": "2023-02-21T10:17:10+00:00" + "time": "2023-03-29T14:47:40+00:00" }, { "name": "slevomat/coding-standard", - "version": "8.8.0", + "version": "8.10.0", "source": { "type": "git", "url": "https://github.com/slevomat/coding-standard.git", - "reference": "59e25146a4ef0a7b194c5bc55b32dd414345db89" + "reference": "c4e213e6e57f741451a08e68ef838802eec92287" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/slevomat/coding-standard/zipball/59e25146a4ef0a7b194c5bc55b32dd414345db89", - "reference": "59e25146a4ef0a7b194c5bc55b32dd414345db89", + "url": "https://api.github.com/repos/slevomat/coding-standard/zipball/c4e213e6e57f741451a08e68ef838802eec92287", + "reference": "c4e213e6e57f741451a08e68ef838802eec92287", "shasum": "" }, "require": { "dealerdirect/phpcodesniffer-composer-installer": "^0.6.2 || ^0.7 || ^1.0", "php": "^7.2 || ^8.0", - "phpstan/phpdoc-parser": ">=1.15.2 <1.16.0", + "phpstan/phpdoc-parser": ">=1.18.0 <1.19.0", "squizlabs/php_codesniffer": "^3.7.1" }, "require-dev": { "phing/phing": "2.17.4", "php-parallel-lint/php-parallel-lint": "1.3.2", - "phpstan/phpstan": "1.4.10|1.9.6", - "phpstan/phpstan-deprecation-rules": "1.1.1", - "phpstan/phpstan-phpunit": "1.0.0|1.3.3", - "phpstan/phpstan-strict-rules": "1.4.4", - "phpunit/phpunit": "7.5.20|8.5.21|9.5.27" + "phpstan/phpstan": "1.4.10|1.10.11", + "phpstan/phpstan-deprecation-rules": "1.1.3", + "phpstan/phpstan-phpunit": "1.0.0|1.3.11", + "phpstan/phpstan-strict-rules": "1.5.1", + "phpunit/phpunit": "7.5.20|8.5.21|9.6.6|10.0.19" }, "type": "phpcodesniffer-standard", "extra": { @@ -3184,7 +3189,7 @@ }, "autoload": { "psr-4": { - "SlevomatCodingStandard\\": "SlevomatCodingStandard" + "SlevomatCodingStandard\\": "SlevomatCodingStandard/" } }, "notification-url": "https://packagist.org/downloads/", @@ -3198,7 +3203,7 @@ ], "support": { "issues": "https://github.com/slevomat/coding-standard/issues", - "source": "https://github.com/slevomat/coding-standard/tree/8.8.0" + "source": "https://github.com/slevomat/coding-standard/tree/8.10.0" }, "funding": [ { @@ -3210,7 +3215,7 @@ "type": "tidelift" } ], - "time": "2023-01-09T10:46:13+00:00" + "time": "2023-04-10T07:39:29+00:00" }, { "name": "squizlabs/php_codesniffer", diff --git a/config/config.neon b/config/config.neon index 607352e..8b7eb47 100644 --- a/config/config.neon +++ b/config/config.neon @@ -21,6 +21,7 @@ dibi: port: %db.port% session: + autoStart: smart savePath: "%tempDir%/sessions" diff --git a/docker-compose.yml b/docker-compose.yml index b339e9c..a08d324 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -2,7 +2,7 @@ version: '3.6' services: web: - image: dockette/web:php-80 + image: dockette/web:php-81 volumes: - ./:/srv ports: @@ -15,7 +15,7 @@ services: database: image: mariadb:latest volumes: - - db/init.sql:/docker-entrypoint-initdb.d/init.sql + - ./db/init.sql:/docker-entrypoint-initdb.d/init.sql ports: - 3306:3306 environment: diff --git a/package-lock.json b/package-lock.json index 731f0ea..f7fc1c1 100644 --- a/package-lock.json +++ b/package-lock.json @@ -10,21 +10,22 @@ "license": "MIT", "dependencies": { "@fortawesome/fontawesome-free": "^6.3.0", - "bootstrap": "^4.4.1", - "bootstrap-datepicker": "^1.9", - "bootstrap-select": "^1.13", - "happy-inputs": "^2.0", - "jquery": "^3.5.0", - "jquery-ui-sortable": "^1.0", - "naja": "^2.2.0", - "nette-forms": "^3.0.0", - "nette.ajax.js": "^2.3", - "popper.js": "^1.14.7", + "bootstrap": "^5.3.0-alpha3", + "naja": "^2.5.0", + "nette-forms": "^3.3.1", "prismjs": "^1.29.0", - "ublaboo-datagrid": "^6.2.13" + "sortablejs": "^1.15.0", + "tom-select": "^2.2.2", + "vanillajs-datepicker": "^1.3.1" }, "devDependencies": { + "@types/bootstrap-select": "^1.13.4", + "@types/jquery": "^3.5.16", + "@types/jqueryui": "^1.12.16", + "@types/sortablejs": "^1.15.1", + "@types/vanillajs-datepicker": "^1.2.1", "autoprefixer": "^10.4.0", + "typescript": "^4.9.5", "vite": "^2.6.10" }, "engines": { @@ -68,6 +69,74 @@ "node": ">=6" } }, + "node_modules/@orchidjs/sifter": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/@orchidjs/sifter/-/sifter-1.0.3.tgz", + "integrity": "sha512-zCZbwKegHytfsPm8Amcfh7v/4vHqTAaOu6xFswBYcn8nznBOuseu6COB2ON7ez0tFV0mKL0nRNnCiZZA+lU9/g==", + "dependencies": { + "@orchidjs/unicode-variants": "^1.0.4" + } + }, + "node_modules/@orchidjs/unicode-variants": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/@orchidjs/unicode-variants/-/unicode-variants-1.0.4.tgz", + "integrity": "sha512-NvVBRnZNE+dugiXERFsET1JlKZfM5lJDEpSMilKW4bToYJ7pxf0Zne78xyXB2ny2c2aHfJ6WLnz1AaTNHAmQeQ==" + }, + "node_modules/@popperjs/core": { + "version": "2.11.7", + "resolved": "https://registry.npmjs.org/@popperjs/core/-/core-2.11.7.tgz", + "integrity": "sha512-Cr4OjIkipTtcXKjAsm8agyleBuDHvxzeBoa1v543lbv1YaIwQjESsVcmjiWiPEbC1FIeHOG/Op9kdCmAmiS3Kw==", + "peer": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/popperjs" + } + }, + "node_modules/@types/bootstrap-select": { + "version": "1.13.4", + "resolved": "https://registry.npmjs.org/@types/bootstrap-select/-/bootstrap-select-1.13.4.tgz", + "integrity": "sha512-jpmfCyF/DETb7P9Ob1htDoSGwSNvdddmBEe47iAbLttWGAGbEzE/Ks6/eGzKzEbDDLbL/melqSW8RkqTpa60Gw==", + "dev": true, + "dependencies": { + "@types/jquery": "*" + } + }, + "node_modules/@types/jquery": { + "version": "3.5.16", + "resolved": "https://registry.npmjs.org/@types/jquery/-/jquery-3.5.16.tgz", + "integrity": "sha512-bsI7y4ZgeMkmpG9OM710RRzDFp+w4P1RGiIt30C1mSBT+ExCleeh4HObwgArnDFELmRrOpXgSYN9VF1hj+f1lw==", + "dev": true, + "dependencies": { + "@types/sizzle": "*" + } + }, + "node_modules/@types/jqueryui": { + "version": "1.12.16", + "resolved": "https://registry.npmjs.org/@types/jqueryui/-/jqueryui-1.12.16.tgz", + "integrity": "sha512-6huAQDpNlso9ayaUT9amBOA3kj02OCeUWs+UvDmbaJmwkHSg/HLsQOoap/D5uveN9ePwl72N45Bl+Frp5xyG1Q==", + "dev": true, + "dependencies": { + "@types/jquery": "*" + } + }, + "node_modules/@types/sizzle": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/@types/sizzle/-/sizzle-2.3.3.tgz", + "integrity": "sha512-JYM8x9EGF163bEyhdJBpR2QX1R5naCJHC8ucJylJ3w9/CVBaskdQ8WqBf8MmQrd1kRvp/a4TS8HJ+bxzR7ZJYQ==", + "dev": true + }, + "node_modules/@types/sortablejs": { + "version": "1.15.1", + "resolved": "https://registry.npmjs.org/@types/sortablejs/-/sortablejs-1.15.1.tgz", + "integrity": "sha512-g/JwBNToh6oCTAwNS8UGVmjO7NLDKsejVhvE4x1eWiPTC3uCuNsa/TD4ssvX3du+MLiM+SHPNDuijp8y76JzLQ==", + "dev": true + }, + "node_modules/@types/vanillajs-datepicker": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@types/vanillajs-datepicker/-/vanillajs-datepicker-1.2.1.tgz", + "integrity": "sha512-j6Rk0IrhuWwztTWcO9mg/fIzVEiqYoOWITI4rGnQiLLsLiaAMqW9E06nfDCBg5HJ94yBn9S7eBFBFC9pJLaiuQ==", + "dev": true + }, "node_modules/autoprefixer": { "version": "10.4.13", "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.13.tgz", @@ -102,9 +171,9 @@ } }, "node_modules/bootstrap": { - "version": "4.6.2", - "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-4.6.2.tgz", - "integrity": "sha512-51Bbp/Uxr9aTuy6ca/8FbFloBUJZLHwnhTcnjIeRn2suQWsWzcuJhGjKDB5eppVte/8oCdOL3VuwxvZDUggwGQ==", + "version": "5.3.0-alpha3", + "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-5.3.0-alpha3.tgz", + "integrity": "sha512-FBhOWMxkCFr74hesJdchLXhqagPTXS+kRNU3gE0FR5Ki/AdPSz32Ik96Z28+yBluCnE/pc9st7l1yPwKgbtfSA==", "funding": [ { "type": "github", @@ -116,25 +185,7 @@ } ], "peerDependencies": { - "jquery": "1.9.1 - 3", - "popper.js": "^1.16.1" - } - }, - "node_modules/bootstrap-datepicker": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/bootstrap-datepicker/-/bootstrap-datepicker-1.9.0.tgz", - "integrity": "sha512-9rYYbaVOheGYxjOr/+bJCmRPihfy+LkLSg4fIFMT9Od8WwWB/MB50w0JO1eBgKUMbb7PFHQD5uAfI3ArAxZRXA==", - "dependencies": { - "jquery": ">=1.7.1 <4.0.0" - } - }, - "node_modules/bootstrap-select": { - "version": "1.13.18", - "resolved": "https://registry.npmjs.org/bootstrap-select/-/bootstrap-select-1.13.18.tgz", - "integrity": "sha512-V1IzK4rxBq5FrJtkzSH6RmFLFBsjx50byFbfAf8jYyXROWs7ZpprGjdHeoyq2HSsHyjJhMMwjsQhRoYAfxCGow==", - "peerDependencies": { - "bootstrap": ">=3.0.0", - "jquery": "1.9.1 - 3" + "@popperjs/core": "^2.11.7" } }, "node_modules/browserslist": { @@ -585,11 +636,6 @@ "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", "dev": true }, - "node_modules/happy-inputs": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/happy-inputs/-/happy-inputs-2.1.0.tgz", - "integrity": "sha512-xv0ulEIUo/1DbuJbl0Rs+3MDy+D7BkDYA710Re1dpeX4mDnqA8+jTZacVNi/xELa2dCjxOkZB84oFAhxoRkRhQ==" - }, "node_modules/has": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", @@ -614,16 +660,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/jquery": { - "version": "3.6.3", - "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.6.3.tgz", - "integrity": "sha512-bZ5Sy3YzKo9Fyc8wH2iIQK4JImJ6R0GWI9kL1/k7Z91ZBNgkRXE6U0JfHIizZbort8ZunhSI3jw9I6253ahKfg==" - }, - "node_modules/jquery-ui-sortable": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/jquery-ui-sortable/-/jquery-ui-sortable-1.0.0.tgz", - "integrity": "sha512-7xAUWoEJ/jHoj48ei8CCUtiad2uM3ie3IR2b3KB0Mpmb54IbBxzVb5vtrj0zqtd0GNQDImx+BPZml9QmK2EL3w==" - }, "node_modules/naja": { "version": "2.5.0", "resolved": "https://registry.npmjs.org/naja/-/naja-2.5.0.tgz", @@ -649,11 +685,6 @@ "resolved": "https://registry.npmjs.org/nette-forms/-/nette-forms-3.3.1.tgz", "integrity": "sha512-UOmA3rF+FjpSci5CGmMtsy79PMWCcl0yyfyCd8YXVS+c68FAnVq3ref5qSxYFcwFynTqcPsYKhsNh8eYW5nVhQ==" }, - "node_modules/nette.ajax.js": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/nette.ajax.js/-/nette.ajax.js-2.3.0.tgz", - "integrity": "sha512-yuWyy+Fkk3bgrNBLu+TyhKquws9GgmJNDQ9rUWZ3NE2Y0OznzG6V+TWF841JD3/VMIU3SXCclceos7oRlpxfbw==" - }, "node_modules/node-releases": { "version": "2.0.8", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.8.tgz", @@ -681,16 +712,6 @@ "integrity": "sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==", "dev": true }, - "node_modules/popper.js": { - "version": "1.16.1", - "resolved": "https://registry.npmjs.org/popper.js/-/popper.js-1.16.1.tgz", - "integrity": "sha512-Wb4p1J4zyFTbM+u6WuO4XstYx4Ky9Cewe4DWrel7B0w6VVICvPwdOpotjzcf6eD8TsckVnIMNONQyPIUFOUbCQ==", - "deprecated": "You can find the new Popper v2 at @popperjs/core, this package is dedicated to the legacy v1", - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/popperjs" - } - }, "node_modules/postcss": { "version": "8.4.21", "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.21.tgz", @@ -766,6 +787,11 @@ "fsevents": "~2.3.2" } }, + "node_modules/sortablejs": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/sortablejs/-/sortablejs-1.15.0.tgz", + "integrity": "sha512-bv9qgVMjUMf89wAvM6AxVvS/4MX3sPeN0+agqShejLU5z5GX4C75ow1O2e5k4L6XItUyAK3gH6AxSbXrOM5e8w==" + }, "node_modules/source-map-js": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.0.2.tgz", @@ -787,10 +813,34 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/ublaboo-datagrid": { - "version": "6.9.1", - "resolved": "https://registry.npmjs.org/ublaboo-datagrid/-/ublaboo-datagrid-6.9.1.tgz", - "integrity": "sha512-b5oaMIJHKPat97xzBwC6BeN8QNSJH5rLzA4yU0SqFm5q4d0tJlsze6knPV0tWWjSV1Z+aaoTgVKX83l4XnZ4Xw==" + "node_modules/tom-select": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/tom-select/-/tom-select-2.2.2.tgz", + "integrity": "sha512-igGah1yY6yhrnN2h/Ky8I5muw/nE/YQxIsEZoYu5qaA4bsRibvKto3s8QZZosKpOd0uO8fNYhRfAwgHB4IAYew==", + "dependencies": { + "@orchidjs/sifter": "^1.0.3", + "@orchidjs/unicode-variants": "^1.0.4" + }, + "engines": { + "node": "*" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/tom-select" + } + }, + "node_modules/typescript": { + "version": "4.9.5", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.9.5.tgz", + "integrity": "sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g==", + "dev": true, + "bin": { + "tsc": "bin/tsc", + "tsserver": "bin/tsserver" + }, + "engines": { + "node": ">=4.2.0" + } }, "node_modules/update-browserslist-db": { "version": "1.0.10", @@ -818,6 +868,11 @@ "browserslist": ">= 4.21.0" } }, + "node_modules/vanillajs-datepicker": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/vanillajs-datepicker/-/vanillajs-datepicker-1.3.1.tgz", + "integrity": "sha512-LYYnXXYDw7oqnNbJleLIRXFUjrG2WYOQtU1A2u3FmW3rgzp7lNJ7DGF35CJ3/Dg1OHUh10D9XnJBfSfIKTyeng==" + }, "node_modules/vite": { "version": "2.9.15", "resolved": "https://registry.npmjs.org/vite/-/vite-2.9.15.tgz", diff --git a/package.json b/package.json index 0306e55..45776c6 100644 --- a/package.json +++ b/package.json @@ -8,21 +8,22 @@ }, "dependencies": { "@fortawesome/fontawesome-free": "^6.3.0", - "bootstrap": "^4.4.1", - "bootstrap-datepicker": "^1.9", - "bootstrap-select": "^1.13", - "happy-inputs": "^2.0", - "jquery": "^3.5.0", - "jquery-ui-sortable": "^1.0", - "naja": "^2.2.0", - "nette-forms": "^3.0.0", - "nette.ajax.js": "^2.3", - "popper.js": "^1.14.7", + "bootstrap": "^5.3.0-alpha3", + "naja": "^2.5.0", + "nette-forms": "^3.3.1", "prismjs": "^1.29.0", - "ublaboo-datagrid": "^6.2.13" + "sortablejs": "^1.15.0", + "tom-select": "^2.2.2", + "vanillajs-datepicker": "^1.3.1" }, "devDependencies": { + "@types/bootstrap-select": "^1.13.4", + "@types/jquery": "^3.5.16", + "@types/jqueryui": "^1.12.16", + "@types/sortablejs": "^1.15.1", + "@types/vanillajs-datepicker": "^1.2.1", "autoprefixer": "^10.4.0", + "typescript": "^4.9.5", "vite": "^2.6.10" }, "scripts": { diff --git a/tsconfig.json b/tsconfig.json new file mode 100644 index 0000000..151801a --- /dev/null +++ b/tsconfig.json @@ -0,0 +1,32 @@ +{ + "compilerOptions": { + "target": "ES2018", + "module": "ESNext", + "moduleResolution": "Node", + "lib": [ + "ESNext", + "ESNext.AsyncIterable", + "DOM" + ], + "esModuleInterop": true, + "allowJs": true, + "sourceMap": true, + "strict": true, + "noEmit": true, + "experimentalDecorators": true, + "baseUrl": ".", + "paths": { + "~/*": [ + "./*" + ], + "@/*": [ + "./*" + ], + "@datagrid": ["./assets/datagrid/index.ts"], + "@datagrid/*": ["./assets/datagrid/*"], + }, + "types": [ + "@types/node" + ] + } +} diff --git a/var/log/.gitignore b/var/log/.gitignore old mode 100644 new mode 100755 diff --git a/var/tmp/.gitignore b/var/tmp/.gitignore old mode 100644 new mode 100755 diff --git a/vite.config.js b/vite.config.js index ff622c9..d6fb3ec 100644 --- a/vite.config.js +++ b/vite.config.js @@ -10,6 +10,7 @@ export default defineConfig(({ mode }) => { alias: { '@': resolve(__dirname, 'assets/js'), '~': resolve(__dirname, 'node_modules'), + '@datagrid': resolve(__dirname, 'assets/datagrid'), }, }, base: '/dist/', From beea9cf59412db113ab7cd297cfa087ca439c283 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 7 Jun 2023 23:51:22 +0200 Subject: [PATCH 31/34] Makefile: setup local.neon --- Makefile | 1 + config/local.neon.dist | 18 +++++++++--------- 2 files changed, 10 insertions(+), 9 deletions(-) diff --git a/Makefile b/Makefile index b51660c..a6709bf 100644 --- a/Makefile +++ b/Makefile @@ -23,6 +23,7 @@ install-node: .PHONY: setup setup: cp -n .env.example .env || true + cp -n config/local.neon.dist config/local.neon || true mkdir -p var/log var/tmp var/tmp/sessions chmod 0777 var/log var/tmp var/tmp/sessions diff --git a/config/local.neon.dist b/config/local.neon.dist index 8af8359..fce0565 100644 --- a/config/local.neon.dist +++ b/config/local.neon.dist @@ -1,9 +1,9 @@ -parameters: - db: - host: database - username: contributte - password: contributte - database: contributte - port: 3306 - -services: +# parameters: +# db: +# host: 0.0.0.0 +# username: contributte +# password: contributte +# database: contributte +# port: 3306 +# +# services: From 5511ee3079d9ef46bcafe13f80389b0088c6fafd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 7 Jun 2023 23:51:17 +0200 Subject: [PATCH 32/34] Env: disable xdebug --- .env.dist | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/.env.dist b/.env.dist index 20a638d..c32499e 100644 --- a/.env.dist +++ b/.env.dist @@ -3,9 +3,8 @@ DB_USER=contributte DB_PASSWORD=contributte DB_ROOT_PASSWORD=contributte -XDEBUG_MODE=debug +XDEBUG_MODE= XDEBUG_HOST=host.docker.internal -XDEBUG_CONFIG= NETTE_DEBUG=0 NETTE_ENV=production From 2dc462e12e6fd06fbbf213238c867c78cf88ed51 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Wed, 7 Jun 2023 23:51:32 +0200 Subject: [PATCH 33/34] Assets: move to datagrid library --- assets/css/main.css | 9 +- assets/datagrid/ajax/index.ts | 1 - assets/datagrid/ajax/naja.ts | 135 ---- assets/datagrid/assets/datagrid.css | 632 ------------------ assets/datagrid/assets/happy.css.ts | 464 ------------- assets/datagrid/datagrid.ts | 152 ----- assets/datagrid/datagrids.ts | 85 --- assets/datagrid/index.ts | 6 - .../datagrid/integrations/bootstrap-select.ts | 46 -- assets/datagrid/integrations/happy.ts | 222 ------ assets/datagrid/integrations/index.ts | 5 - assets/datagrid/integrations/sortable-js.ts | 58 -- assets/datagrid/integrations/tom-select.ts | 23 - .../integrations/vanilla-datepicker.ts | 14 - .../datagrid/plugins/features/autosubmit.ts | 69 -- .../datagrid/plugins/features/checkboxes.ts | 92 --- assets/datagrid/plugins/features/confirm.ts | 28 - assets/datagrid/plugins/features/editable.ts | 118 ---- assets/datagrid/plugins/features/inline.ts | 73 -- .../datagrid/plugins/features/item-detail.ts | 51 -- assets/datagrid/plugins/features/treeView.ts | 39 -- assets/datagrid/plugins/index.ts | 12 - .../plugins/integrations/datepicker.ts | 17 - assets/datagrid/plugins/integrations/happy.ts | 19 - .../plugins/integrations/nette-forms.ts | 18 - .../plugins/integrations/selectpicker.ts | 17 - .../datagrid/plugins/integrations/sortable.ts | 62 -- assets/datagrid/types/ajax.d.ts | 136 ---- assets/datagrid/types/datagrid.d.ts | 29 - assets/datagrid/types/index.d.ts | 40 -- assets/datagrid/types/integrations.d.ts | 14 - assets/datagrid/utils.ts | 180 ----- assets/js/main.js | 36 +- package-lock.json | 157 +++-- package.json | 1 + vite.config.js | 1 - 36 files changed, 118 insertions(+), 2943 deletions(-) delete mode 100644 assets/datagrid/ajax/index.ts delete mode 100644 assets/datagrid/ajax/naja.ts delete mode 100644 assets/datagrid/assets/datagrid.css delete mode 100644 assets/datagrid/assets/happy.css.ts delete mode 100644 assets/datagrid/datagrid.ts delete mode 100644 assets/datagrid/datagrids.ts delete mode 100644 assets/datagrid/index.ts delete mode 100644 assets/datagrid/integrations/bootstrap-select.ts delete mode 100644 assets/datagrid/integrations/happy.ts delete mode 100644 assets/datagrid/integrations/index.ts delete mode 100644 assets/datagrid/integrations/sortable-js.ts delete mode 100644 assets/datagrid/integrations/tom-select.ts delete mode 100644 assets/datagrid/integrations/vanilla-datepicker.ts delete mode 100644 assets/datagrid/plugins/features/autosubmit.ts delete mode 100644 assets/datagrid/plugins/features/checkboxes.ts delete mode 100644 assets/datagrid/plugins/features/confirm.ts delete mode 100644 assets/datagrid/plugins/features/editable.ts delete mode 100644 assets/datagrid/plugins/features/inline.ts delete mode 100644 assets/datagrid/plugins/features/item-detail.ts delete mode 100644 assets/datagrid/plugins/features/treeView.ts delete mode 100644 assets/datagrid/plugins/index.ts delete mode 100644 assets/datagrid/plugins/integrations/datepicker.ts delete mode 100644 assets/datagrid/plugins/integrations/happy.ts delete mode 100644 assets/datagrid/plugins/integrations/nette-forms.ts delete mode 100644 assets/datagrid/plugins/integrations/selectpicker.ts delete mode 100644 assets/datagrid/plugins/integrations/sortable.ts delete mode 100644 assets/datagrid/types/ajax.d.ts delete mode 100644 assets/datagrid/types/datagrid.d.ts delete mode 100644 assets/datagrid/types/index.d.ts delete mode 100644 assets/datagrid/types/integrations.d.ts delete mode 100644 assets/datagrid/utils.ts diff --git a/assets/css/main.css b/assets/css/main.css index 2f39b39..f608161 100644 --- a/assets/css/main.css +++ b/assets/css/main.css @@ -1,9 +1,6 @@ -@import "@fortawesome/fontawesome-free/css/all.css"; -@import 'bootstrap/dist/css/bootstrap.css'; -@import 'prismjs/themes/prism-okaidia.css'; - -@import './../datagrid/assets/datagrid.css'; -@import 'vanillajs-datepicker/css/datepicker-bs5.css'; +/* Datagrid styles */ +@import '@contributte/datagrid/assets/css/datagrid-full.css'; /* App styles */ +@import 'prismjs/themes/prism-okaidia.css'; @import './styles.css'; diff --git a/assets/datagrid/ajax/index.ts b/assets/datagrid/ajax/index.ts deleted file mode 100644 index 23b37df..0000000 --- a/assets/datagrid/ajax/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from "./naja"; diff --git a/assets/datagrid/ajax/naja.ts b/assets/datagrid/ajax/naja.ts deleted file mode 100644 index b9d0840..0000000 --- a/assets/datagrid/ajax/naja.ts +++ /dev/null @@ -1,135 +0,0 @@ -import type {Naja} from "naja"; -import type { - Ajax, - RequestParams, - Payload, - DatagridPayload, - EventDetail, - EventListener, - Response as AjaxResponse, - BaseRequestParams as AjaxBaseRequestParams, - BeforeEventDetail as BaseBeforeEventDetail, - ErrorEventDetail as BaseErrorEventDetail, - InteractEventDetail as BaseInteractEventDetail, - SuccessEventDetail as BaseSuccessEventDetail, - AjaxEventMap as BaseAjaxEventMap, -} from "@datagrid/types"; -import {Datagrid} from "@datagrid/datagrid"; -import {BeforeEvent, SuccessEvent, ErrorEvent, Payload as NajaPayload} from "naja/dist/Naja"; -import {InteractionEvent} from "naja/dist/core/UIHandler"; - -export interface BaseRequestParams extends AjaxBaseRequestParams, Request { - url: string; - method: string; -} - -export interface BeforeEventDetail extends BaseBeforeEventDetail { - params: EventDetail & RequestParams; -} - -export interface InteractEventDetail< - E extends HTMLElement = HTMLElement -> extends BaseInteractEventDetail, EventDetail { - element: E; -} - -export interface SuccessEventDetail< - P = DatagridPayload -> extends BaseSuccessEventDetail, EventDetail { - params: BaseRequestParams; - payload: Payload

& NajaPayload; - response: AjaxResponse & Response; -} - -export interface ErrorEventDetail< - E extends Error = Error, -> extends BaseErrorEventDetail, EventDetail { - params: BaseRequestParams; - response: (AjaxResponse & Response) | undefined; - error: E; -} - -export interface AjaxEventMap extends BaseAjaxEventMap { - before: CustomEvent; - interact: CustomEvent; - snippetUpdate: CustomEvent; - success: CustomEvent; - error: CustomEvent; -} - -export class NajaAjax extends EventTarget implements Ajax { - constructor(public client: C) { - if (!client.VERSION || client.VERSION < 2) { - throw new Error("NajaAjax supports Naja 2 and higher" + (client.VERSION ? `(version ${client.VERSION} provided)` : '')) - } - super(); - } - - onInit() { - this.client.addEventListener('before', (e) => { - return this.dispatch('before', { - params: e.detail - }); - }) - - this.client.uiHandler.addEventListener('interaction', (e) => { - if (!(e.detail.element instanceof HTMLElement)) { - throw new Error("Element is not an instanceof HTMLElement"); - } - - return this.dispatch('interact', { - ...e.detail, - element: e.detail.element as HTMLElement // Naja's event has a type of HTMLElement - }) - }) - - - this.client.addEventListener('success', (e) => { - return this.dispatch('success', { - ...e.detail, - params: e.detail.request, - payload: e.detail.payload as Payload - }); - }) - - this.client.addEventListener('error', (e) => { - return this.dispatch('error', { - ...e.detail, - params: e.detail.request, - response: e.detail.response, - }); - }) - - return this; - } - - async request(args: RequestParams): Promise

{ - return await this.client.makeRequest(args.method, args.url, args.data) as P; - } - - async submitForm(element: E): Promise

{ - return await this.client.uiHandler.submitForm(element) as P; - } - - dispatch< - K extends string, M extends BaseAjaxEventMap = AjaxEventMap - >(type: K, detail: K extends keyof M ? EventDetail : any, options?: boolean): boolean { - return this.dispatchEvent(new CustomEvent(type, {detail})); - } - - declare addEventListener: ( - type: K, - listener: EventListener, - options?: boolean | AddEventListenerOptions - ) => void; - - declare removeEventListener: ( - type: K, - listener: EventListener, - options?: boolean | AddEventListenerOptions - ) => void; - - declare dispatchEvent: ( - event: K extends keyof M ? M[K] : CustomEvent - ) => boolean; -} diff --git a/assets/datagrid/assets/datagrid.css b/assets/datagrid/assets/datagrid.css deleted file mode 100644 index 8b096ce..0000000 --- a/assets/datagrid/assets/datagrid.css +++ /dev/null @@ -1,632 +0,0 @@ -/* .datagrid--slide-toggle > td > div { - -webkit-transition: height .25s ease; - -o-transition: height .25s ease; - transition: height .25s ease; - overflow: hidden; -} */ - -.datagrid--content-row:not(.is-active) > td /*> div*/ { - display: none; -} - -@keyframes edited { - 0% { - background-color: #A6E2A9 - } - - 100% { - background-color: transparent - } - -} - -@keyframes edited-error { - 0% { - background-color: #E8AAA4 - } - - 100% { - background-color: transparent - } - -} - -.datagrid { - background-color: #fff; - padding: 1em; - box-sizing: border-box -} - -.datagrid .datagrid-input-group-full-width { - width: 100% -} - -.datagrid .hidden { - display: none !important -} - -.datagrid .datagrid-collapse-filters-button-row { - margin-bottom: 0.5em -} - -.datagrid .col-action .dropdown { - display: inline-block -} - -.datagrid .datagrid-row-inline-add.datagrid-row-inline-add-hidden { - display: none -} - -.datagrid .datagrid-row-columns-summary td { - border-top: 2px solid #bbb; - border-left: 1px solid #eee; - border-right: 1px solid #eee; - font-weight: bold -} - -.datagrid .datagrid-row-columns-summary td:first-child { - border-left: 1px solid #ddd -} - -.datagrid .datagrid-row-columns-summary td:last-child { - border-right: 1px solid #ddd -} - -.datagrid .datagrid-toolbar { - margin-top: .35em; - float: right; - display: inline-block -} - -.datagrid .datagrid-toolbar > span { - margin-left: 1em -} - -.datagrid .datagrid-toolbar > span > a { - margin-left: 0.5em -} - -.datagrid-toolbar .fa-square, .datagrid-toolbar .fa-check-square { - font-weight: normal; -} - -.datagrid .datagrid-exports .btn { - margin-left: 0.5em -} - -.datagrid .datagrid-exports .btn:first-child { - margin-left: 0 -} - -.datagrid .datagrid-settings { - display: inline-block -} - -.datagrid .datagrid-settings .dropdown-menu--grid { - font-size: 12px -} - -.datagrid .datagrid-settings .dropdown-menu--grid li .fa { - margin-right: 0.5em -} - -.datagrid .row-reset-filter { - text-align: right; - margin-bottom: 0.5em -} - -.datagrid .row-filters .datagrid-row-outer-filters-group { - margin-bottom: 0.5em -} - -.datagrid .datagrid-manual-submit { - margin-bottom: 0.5em -} - -.datagrid .filter-range-delimiter { - text-align: center -} - -.datagrid .bootstrap-select.input-sm > .btn { - padding: 5px 25px 5px 10px; - font-size: 12px; - line-height: 1.5; - border-radius: 3px -} - -.datagrid table { - margin: 0 -} - -.datagrid table thead tr .bootstrap-select:not([class*=col-]):not(.input-group-btn) { - width: auto -} - -.datagrid table thead tr .bootstrap-select:not([class*=col-]):not(.input-group-btn) > .btn { - width: auto -} - -.datagrid table thead tr .bootstrap-select:not([class*=col-]):not(.input-group-btn) .dropdown-menu li { - font-size: 13px -} - -.datagrid table thead tr.row-group-actions th { - border-bottom-width: 0 !important; - background-color: #f9f9f9 -} - -.datagrid table thead tr.row-group-actions .datagrid-selected-rows-count { - margin-left: 0.3em -} - -.datagrid table thead tr th { - font-size: 90%; - vertical-align: top -} - -.datagrid table thead tr th hr { - margin: 8px -8px -} - -.datagrid table thead tr th .datagrid-column-header-additions { - float: right -} - -.datagrid table thead tr th .datagrid-column-header-additions a[data-datagrid-reset-filter-by-column] { - margin-left: 0.3em; - color: #858585 -} - -.datagrid table thead tr th .datagrid-column-header-additions .column-settings-menu { - opacity: 0; - cursor: pointer; - margin-left: 0.3em; - display: inline-block -} - -.datagrid table thead tr th .datagrid-column-header-additions .column-settings-menu .dropdown-menu { - font-size: 12px -} - -.datagrid table thead tr th .datagrid-column-header-additions .column-settings-menu .dropdown-menu li .fa { - margin-right: 0.5em -} - -.datagrid table thead tr th .datagrid-column-header-additions .column-settings-menu .dropdown-toggle::after { - display: none !important -} - -.datagrid .datagrid-col-filter-date-range { - width: auto; - position: relative; - display: flex; - flex-wrap: wrap; - align-items: stretch; -} - -.datagrid .datagrid-col-filter-date-range > .input-group { - position: relative; - -ms-flex: 1 1 auto; - flex: 1 1 auto; - width: 1%; - margin-bottom: 0; -} - -.datagrid .datagrid-col-filter-datte-range-delimiter { - background-color: inherit; - border: none; - padding: .25rem .5rem -} - -.datagrid table thead tr th .datagrid-col-filter-range .form-control { - -webkit-border-radius: 3px; - -moz-border-radius: 3px; - border-radius: 3px -} - -.datagrid table thead tr th:hover .column-settings-menu { - opacity: 1 -} - -.datagrid table tbody td { - vertical-align: middle -} - -.datagrid table tbody tr.ui-sortable-helper { - display: table -} - -.datagrid table tbody tr .datagrid-inline-edit .form-control { - margin: -3px; - padding-bottom: 4px; - padding-top: 4px; - height: 28px -} - -.datagrid table tbody tr td[data-datagrid-editable-url].editing textarea { - padding: 2px; - margin: -3px -} - -.datagrid table tbody tr td.edited { - animation-name: edited; - animation-duration: 1.2s; - animation-delay: 0 -} - -.datagrid table tbody tr td.edited-error { - animation-name: edited-error; - animation-duration: 1.6s; - animation-delay: 0 -} - -.datagrid table th.col-checkbox, .datagrid table td.col-checkbox { - padding: 0; - width: 2.1em; - text-align: center; - vertical-align: middle -} - -.datagrid table th.col-checkbox .happy-checkbox, .datagrid table td.col-checkbox .happy-checkbox { - margin-right: 0 -} - -.datagrid table th.col-checkbox.col-checkbox-first, .datagrid table td.col-checkbox.col-checkbox-first { - border-top-color: transparent -} - -.datagrid table th.col-checkbox { - background-color: #f9f9f9 -} - -.datagrid table th.col-action, .datagrid table td.col-action { - white-space: nowrap; - width: 10px -} - -.datagrid table th.col-action { - text-align: center -} - -.datagrid table td.col-action { - text-align: right -} - -.datagrid table th.datagrid-fit-content, .datagrid table td.datagrid-fit-content { - width: 1%; - white-space: nowrap -} - -.datagrid .datagrid-tree > .datagrid-tree-header .datagrid-tree-item-right-actions-action { - opacity: 0 -} - -.datagrid .datagrid-tree > .datagrid-tree-item { - margin-left: 20px -} - -.datagrid .datagrid-tree .datagrid-tree-item { - position: relative -} - -.datagrid .datagrid-tree .datagrid-tree-item.ui-sortable-placeholder { - visibility: visible !important; - background-color: rgba(70, 83, 93, 0.1) -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content { - position: relative; - display: flex; - flex-direction: row; - flex-wrap: nowrap; - justify-content: space-between; - box-sizing: border-box; - height: 37px; - box-shadow: inset 0px -1px 1px -1px #9B9B9B -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left, .datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right { - display: flex; - flex-direction: row; - flex-wrap: nowrap; - justify-content: space-between; - align-items: center -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left { - order: 1 -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left > .chevron { - -webkit-border-radius: 11px; - -moz-border-radius: 11px; - border-radius: 11px; - width: 22px; - height: 22px; - line-height: 20px; - vertical-align: middle; - background-color: #fff; - display: inline-block; - text-align: center; - position: relative; - margin: 0 5px 0 -27px; - transition: transform 0.2s ease-in-out -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left > .chevron:hover { - -webkit-box-shadow: 0px 0px 3px 0px #b4b4b4; - -moz-box-shadow: 0px 0px 3px 0px #b4b4b4; - box-shadow: 0px 0px 3px 0px #b4b4b4 -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left > .chevron.toggle-rotate { - transform: rotate(90deg) -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-left > .chevron .fa { - font-size: 10px; - transform: translate(1px, 0) -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right { - position: relative; - order: 2; - flex-basis: 50%; - display: flex; - flex-wrap: nowrap; - justify-content: flex-end; - flex-direction: row -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .btn { - margin-top: -3px -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-columns { - white-space: nowrap; - display: flex; - flex-basis: 70%; - flex-direction: row; - flex-wrap: nowrap; - justify-content: flex-end -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-columns .datagrid-tree-item-right-columns-column { - padding: 0 7px; - margin-right: 4px; - flex-basis: 25% -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-columns .datagrid-tree-item-right-columns-column:last-child { - margin-right: 0 -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-actions { - margin-left: 7px; - display: flex; - flex-direction: row; - flex-wrap: nowrap; - justify-content: space-between; - align-items: center -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-actions .datagrid-tree-item-right-actions-action { - margin-right: 4px -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-content .datagrid-tree-item-right .datagrid-tree-item-right-actions .datagrid-tree-item-right-actions-action:last-child { - margin-right: 0 -} - -.datagrid .datagrid-tree .datagrid-tree-item .datagrid-tree-item-children:not(.datagrid-tree) { - margin-left: 28px -} - -.datagrid .datagrid-tree .datagrid-tree-item:not(.has-children) > .datagrid-tree-item-children { - box-sizing: border-box; - position: relative; - width: calc(100% - 28px); - min-height: 9px; - margin-top: -9px -} - -.datagrid .datagrid-tree .datagrid-tree-item.has-children > .datagrid-tree-item-children { - display: none -} - -.datagrid .datagrid-tree .datagrid-tree-item.has-children > .datagrid-tree-item-children .datagrid-tree-item-right { - flex-basis: calc(50% + 14px) -} - -.datagrid .datagrid-tree-item-children .datagrid-tree-item-right { - flex-basis: calc(50% + 14px) -} - -.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { - flex-basis: calc(50% + 28px) !important -} - -.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { - flex-basis: calc(50% + 42px) !important -} - -.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { - flex-basis: calc(50% + 56px) !important -} - -.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { - flex-basis: calc(50% + 74px) !important -} - -.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { - flex-basis: calc(50% + 88px) !important -} - -.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { - flex-basis: calc(50% + 102px) !important -} - -.datagrid .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-children .datagrid-tree-item-right { - flex-basis: calc(50% + 116px) !important -} - -.datagrid .btn { - transition: all 0.1s ease-in-out; - white-space: nowrap -} - -.datagrid select { - padding: 0; - text-transform: none -} - -.datagrid .row-grid-bottom { - font-size: 0; - padding: 8px; - background-color: #f9f9f9; - border: 1px solid #ddd; - border-top: 0 -} - -.datagrid .row-grid-bottom .col-items { - font-size: 14px; - display: inline-block; - width: 25% -} - -.datagrid .row-grid-bottom .col-pagination { - font-size: 14px; - display: inline-block; - width: 50% -} - -.datagrid .row-grid-bottom .col-per-page { - font-size: 14px; - display: inline-block; - width: 25% -} - -.datagrid .row-grid-bottom .col-per-page form { - display: inline-block -} - -.datagrid .row-grid-bottom .col-per-page .form-control { - width: auto; - display: inline-block -} - -.datagrid .row-grid-bottom .datagrid-per-page-submit { - position: absolute; - visibility: hidden; - width: 0; - top: -200px -} - -.datagrid .pagination.active > span { - color: #fff -} - -.datagrid .pagination > a.disabled { - color: #989898; - cursor: not-allowed -} - -.datagrid .pagination > a.active { - pointer-events: none; - cursor: default -} - -.datagrid .row-group-actions th { - font-weight: normal -} - -.datagrid .col-checkbox { - -webkit-touch-callout: none; - -webkit-user-select: none; - -khtml-user-select: none; - -moz-user-select: none; - -ms-user-select: none; - user-select: none -} - -.datagrid .col-checkbox .happy-checkbox { - margin-top: 2px -} - -.datagrid .datagrid-column-status-option-icon { - float: right -} - -@media (min-width: 768px) { - .datagrid .ublaboo-datagrid-th-form-inline .form-group { - display: inline-block; - margin-bottom: 0; - vertical-align: middle - } - - .datagrid .ublaboo-datagrid-th-form-inline .form-control { - display: inline-block; - width: auto; - vertical-align: middle - } - - .datagrid .ublaboo-datagrid-th-form-inline .form-control[hidden] { - display: none; - } - - .ublaboo-datagrid-th-form-inline .form-control[hidden] { - display: none; - } - - .datagrid .ublaboo-datagrid-th-form-inline .input-group { - display: inline-table; - vertical-align: middle - } - - .datagrid .ublaboo-datagrid-th-form-inline .input-group .form-control { - width: auto - } - - .datagrid .ublaboo-datagrid-th-form-inline .input-group > .form-control { - width: 100% - } - - .datagrid .input-group-text { - height: calc(1.5em + 0.5rem + 2px); - } - - .datagrid .ublaboo-datagrid-th-form-inline .control-label { - margin-bottom: 0; - vertical-align: middle - } - - .datagrid .ublaboo-datagrid-th-form-inline .radio, .datagrid .ublaboo-datagrid-th-form-inline .checkbox { - display: inline-block; - margin-top: 0; - margin-bottom: 0; - vertical-align: middle - } - - .datagrid .ublaboo-datagrid-th-form-inline .radio label, .datagrid .ublaboo-datagrid-th-form-inline .checkbox label { - padding-left: 0 - } - - .datagrid .ublaboo-datagrid-th-form-inline .radio input[type="radio"], .datagrid .ublaboo-datagrid-th-form-inline .checkbox input[type="checkbox"] { - position: relative; - margin-left: 0 - } - -} - -.datagrid .btn-xs, .datagrid .btn-group-xs > .btn { - padding: 1px 5px; - font-size: 12px; - line-height: 1.5; - border-radius: 3px -} - -.datagrid .dropdown-item { - padding: 3px 20px; - line-height: 1.42857143; - font-size: 12px; -} diff --git a/assets/datagrid/assets/happy.css.ts b/assets/datagrid/assets/happy.css.ts deleted file mode 100644 index 525ffbc..0000000 --- a/assets/datagrid/assets/happy.css.ts +++ /dev/null @@ -1,464 +0,0 @@ -export const happyStyles = `/** - * From happy-inputs by paveljanda: - * https://github.com/paveljanda/happy/blob/94357b7146b5f3029cc565859a588c5832dd374a/src/happy.css - */ - -.happy-color, -.happy-checkbox, -.happy-radio { - color: #333333; -} - -.happy-color > b, -.happy-checkbox > b, -.happy-radio > b { - background-color: #333333; -} - -.happy-color.active, -.active.happy-checkbox, -.active.happy-radio { - color: #333333; -} - -.happy-color.active > b, -.active.happy-checkbox > b, -.active.happy-radio > b { - background-color: #333333; -} - -.happy-color.primary, -.primary.happy-checkbox, -.primary.happy-radio { - color: #333333; -} - -.happy-color.primary > b, -.primary.happy-checkbox > b, -.primary.happy-radio > b { - background-color: #333333; -} - -.happy-color.primary.active, -.primary.active.happy-checkbox, -.primary.active.happy-radio { - color: #4c86bb; -} - -.happy-color.primary.active > b, -.primary.active.happy-checkbox > b, -.primary.active.happy-radio > b { - background-color: #4c86bb; -} - -.happy-color.success, -.success.happy-checkbox, -.success.happy-radio { - color: #333333; -} - -.happy-color.success > b, -.success.happy-checkbox > b, -.success.happy-radio > b { - background-color: #333333; -} - -.happy-color.success.active, -.success.active.happy-checkbox, -.success.active.happy-radio { - color: #72b889; -} - -.happy-color.success.active > b, -.success.active.happy-checkbox > b, -.success.active.happy-radio > b { - background-color: #72b889; -} - -.happy-color.info, -.info.happy-checkbox, -.info.happy-radio { - color: #333333; -} - -.happy-color.info > b, -.info.happy-checkbox > b, -.info.happy-radio > b { - background-color: #333333; -} - -.happy-color.info.active, -.info.active.happy-checkbox, -.info.active.happy-radio { - color: #5bc0de; -} - -.happy-color.info.active > b, -.info.active.happy-checkbox > b, -.info.active.happy-radio > b { - background-color: #5bc0de; -} - -.happy-color.warning, -.warning.happy-checkbox, -.warning.happy-radio { - color: #333333; -} - -.happy-color.warning > b, -.warning.happy-checkbox > b, -.warning.happy-radio > b { - background-color: #333333; -} - -.happy-color.warning.active, -.warning.active.happy-checkbox, -.warning.active.happy-radio { - color: #f0bb65; -} - -.happy-color.warning.active > b, -.warning.active.happy-checkbox > b, -.warning.active.happy-radio > b { - background-color: #f0bb65; -} - -.happy-color.danger, -.danger.happy-checkbox, -.danger.happy-radio { - color: #333333; -} - -.happy-color.danger > b, -.danger.happy-checkbox > b, -.danger.happy-radio > b { - background-color: #333333; -} - -.happy-color.danger.active, -.danger.active.happy-checkbox, -.danger.active.happy-radio { - color: #ed6b6b; -} - -.happy-color.danger.active > b, -.danger.active.happy-checkbox > b, -.danger.active.happy-radio > b { - background-color: #ed6b6b; -} - -.happy-color.white, -.white.happy-checkbox, -.white.happy-radio { - color: #333333; -} - -.happy-color.white > b, -.white.happy-checkbox > b, -.white.happy-radio > b { - background-color: #333333; -} - -.happy-color.white.active, -.white.active.happy-checkbox, -.white.active.happy-radio { - color: #ffffff; -} - -.happy-color.white.active > b, -.white.active.happy-checkbox > b, -.white.active.happy-radio > b { - background-color: #ffffff; -} - -.happy-border-color, -.happy-radio { - border-color: rgba(51, 51, 51, 0.8); -} - -.happy-border-color.active, -.active.happy-radio { - border-color: #333333; -} - -.happy-border-color.primary, -.primary.happy-radio { - border-color: rgba(51, 51, 51, 0.8); -} - -.happy-border-color.primary.active, -.primary.active.happy-radio { - border-color: #4c86bb; -} - -.happy-border-color.success, -.success.happy-radio { - border-color: rgba(51, 51, 51, 0.8); -} - -.happy-border-color.success.active, -.success.active.happy-radio { - border-color: #72b889; -} - -.happy-border-color.info, -.info.happy-radio { - border-color: rgba(51, 51, 51, 0.8); -} - -.happy-border-color.info.active, -.info.active.happy-radio { - border-color: #5bc0de; -} - -.happy-border-color.warning, -.warning.happy-radio { - border-color: rgba(51, 51, 51, 0.8); -} - -.happy-border-color.warning.active, -.warning.active.happy-radio { - border-color: #f0bb65; -} - -.happy-border-color.danger, -.danger.happy-radio { - border-color: rgba(51, 51, 51, 0.8); -} - -.happy-border-color.danger.active, -.danger.active.happy-radio { - border-color: #ed6b6b; -} - -.happy-border-color.white, -.white.happy-radio { - border-color: rgba(51, 51, 51, 0.8); -} - -.happy-border-color.white.active, -.white.active.happy-radio { - border-color: #ffffff; -} - -/** - * Common - */ - -input[type="radio"].happy, -input[type="checkbox"].happy { - position: absolute; - top: -50%; - left: -50%; - opacity: 0; -} - -label:not(.selectable), -.noselect { - -webkit-touch-callout: none; - -webkit-user-select: none; - -khtml-user-select: none; - -moz-user-select: none; - -ms-user-select: none; - user-select: none; -} - -label { - cursor: pointer; - position: relative; -} - -/** - * Checkbox - */ - -.happy-checkbox { - border-color: #333333; - margin-right: 0.2em; - position: relative; - display: inline-block; - line-height: 20px; - vertical-align: middle; - width: 16px; - height: 16px; - border-width: 2px; - border-style: solid; - cursor: pointer; - box-sizing: border-box; - top: -2px; - -webkit-border-radius: 2.66667px; - -moz-border-radius: 2.66667px; - border-radius: 2.66667px; -} - -.happy-checkbox svg { - position: absolute; - display: block; - top: -2px; - left: -2px; - height: 16px; - width: 16px; - opacity: 0; - -webkit-border-radius: 2.66667px; - -moz-border-radius: 2.66667px; - border-radius: 2.66667px; - background-color: #333333; - -ms-transform: scale(0.4); - -webkit-transform: scale(0.4); - transform: scale(0.4); - -ms-transition: all 180ms; - -webkit-transition: all 180ms; - transition: all 180ms; -} - -.happy-checkbox svg rect { - fill: white; -} - -.happy-checkbox svg rect:first-child { - -ms-transform: rotate(45deg); - -webkit-transform: rotate(45deg); - transform: rotate(45deg); -} - -.happy-checkbox svg rect:nth-child(2) { - -ms-transform: rotate(-45deg); - -webkit-transform: rotate(-45deg); - transform: rotate(-45deg); - /* fill: yellow; */ -} - -.happy-checkbox.thin { - border-width: 1px; -} - -.happy-checkbox.thin svg { - top: -1px; - left: -1px; -} - -.happy-checkbox.white { - border-color: #ffffff; -} - -.happy-checkbox.gray-border { - border-color: #858585; -} - -.happy-checkbox.primary-border { - border-color: #4c86bb; -} - -.happy-checkbox.success-border { - border-color: #72b889; -} - -.happy-checkbox.info-border { - border-color: #5bc0de; -} - -.happy-checkbox.warning-border { - border-color: #f0bb65; -} - -.happy-checkbox.danger-border { - border-color: #ed6b6b; -} - -.happy-checkbox.primary svg { - background-color: #4c86bb; -} - -.happy-checkbox.success svg { - background-color: #72b889; -} - -.happy-checkbox.info svg { - background-color: #5bc0de; -} - -.happy-checkbox.warning svg { - background-color: #f0bb65; -} - -.happy-checkbox.danger svg { - background-color: #ed6b6b; -} - -.happy-checkbox.white svg { - background-color: #ffffff; -} - -.happy-checkbox.white svg rect { - fill: #333333; -} - -.happy-checkbox.active { - border-color: transparent; -} - -.happy-checkbox.active svg { - opacity: 1; - -ms-transform: scale(1); - -webkit-transform: scale(1); - transform: scale(1); -} - -/** - * Radio - */ - -.happy-radio { - position: relative; - display: inline-block; - line-height: 20px; - vertical-align: middle; - width: 16px; - height: 16px; - border-width: 2px; - border-style: solid; - cursor: pointer; - box-sizing: border-box; - top: -2px; - -webkit-border-radius: 16px; - -moz-border-radius: 16px; - border-radius: 16px; -} - -.happy-radio.thin { - border-width: 1.66667px; -} - -.happy-radio b { - position: absolute; - display: block; - top: 2px; - left: 2px; - bottom: 2px; - right: 2px; - opacity: 0; - -webkit-border-radius: 10.66667px; - -moz-border-radius: 10.66667px; - border-radius: 10.66667px; - -ms-transform: scale(0.4); - -webkit-transform: scale(0.4); - transform: scale(0.4); - -ms-transition: all 180ms; - -webkit-transition: all 180ms; - transition: all 180ms; -} - -.happy-radio.active b { - opacity: 1; - -ms-transform: scale(1); - -webkit-transform: scale(1); - transform: scale(1); -} - -.happy-radio.focus { - outline: none; - -webkit-box-shadow: 0px 0px 5px 0px rgba(50, 50, 50, 0.75); - -moz-box-shadow: 0px 0px 5px 0px rgba(50, 50, 50, 0.75); - box-shadow: 0px 0px 5px 0px rgba(50, 50, 50, 0.75); -} -`; diff --git a/assets/datagrid/datagrid.ts b/assets/datagrid/datagrid.ts deleted file mode 100644 index 337ed32..0000000 --- a/assets/datagrid/datagrid.ts +++ /dev/null @@ -1,152 +0,0 @@ -import {defaultDatagridNameResolver, isEnter} from "@datagrid/utils"; -import type { - DatagridEventMap, - EventListener, - Ajax, - DatagridOptions, EventDetail, -} from "@datagrid/types"; - -export class Datagrid extends EventTarget { - private static readonly defaultOptions: DatagridOptions = { - confirm: confirm, - resolveDatagridName: defaultDatagridNameResolver, - plugins: [], - }; - - public readonly name: string; - - public readonly ajax: Ajax; - - private readonly options: DatagridOptions; - - constructor( - public readonly el: HTMLElement, - ajax: Ajax | ((grid: Datagrid) => Ajax), - options: Partial - ) { - super(); - - this.options = { - ...Datagrid.defaultOptions, - ...options, - }; - - const name = this.resolveDatagridName(); - - if (!name) { - throw new Error("Cannot resolve name of a datagrid!"); - } - - this.name = name; - - this.ajax = typeof ajax === "function" ? ajax(this) : ajax; - - this.ajax.addEventListener("success", e => { - if (e.detail.payload?._datagrid_name === this.name && e.detail.payload?._datagrid_init) { - this.init(); - } - }); - - this.init(); - } - - public init() { - console.log("init") - - let cancelled = !this.dispatch('beforeInit', {datagrid: this}) - if (!cancelled) { - this.options.plugins.forEach((plugin) => { - plugin.onDatagridInit?.(this) - }) - } - - // Uncheck toggle-all - const checkedRows = this.el.querySelectorAll("input[data-check]:checked"); - if (checkedRows.length === 1 && checkedRows[0].getAttribute("name") === "toggle-all") { - const input = checkedRows[0]; - if (input) { - input.checked = false; - } - } - - this.el.querySelectorAll("input[data-datagrid-manualsubmit]").forEach(inputEl => { - const form = inputEl.closest("form"); - if (!form) return; - - inputEl.addEventListener("keydown", e => { - if (!isEnter(e)) return; - - e.stopPropagation(); - e.preventDefault(); - return this.ajax.submitForm(form); - }); - }); - - this.ajax.addEventListener("success", ({detail: {payload}}) => { - // todo: maybe move? - if (payload._datagrid_name && payload._datagrid_name === this.name) { - this.el.querySelector("[data-datagrid-reset-filter-by-column]") - ?.classList.add("hidden"); - - if (payload.non_empty_filters && payload.non_empty_filters.length >= 1) { - const resets = Array.from(this.el.querySelectorAll( - `[data-datagrid-reset-filter-by-column]` - )); - - const getColumnName = (el: HTMLElement) => el.getAttribute( - "data-datagrid-reset-filter-by-column" - ) - - /// tf? - for (const columnName of payload.non_empty_filters) { - resets.find(getColumnName)?.classList.remove("hidden"); - } - - const href = this.el.querySelector(".reset-filter") - ?.getAttribute("href"); - - if (href) { - resets.forEach((el) => { - const columnName = getColumnName(el); - - const newHref = href.replace("-resetFilter", "-resetColumnFilter"); - el.setAttribute("href", `${newHref}&${this.name}-key=${columnName}`); - }) - } - } - } - }) - - this.dispatch('afterInit', {datagrid: this}); - } - - public confirm(message: string): boolean { - return this.options.confirm.bind(this)(message); - } - - public resolveDatagridName(): string | null { - return this.options.resolveDatagridName.bind(this)(this.el); - } - - dispatch< - K extends string, M extends DatagridEventMap = DatagridEventMap - >(type: K, detail: K extends keyof M ? EventDetail : any, options?: boolean): boolean { - return this.dispatchEvent(new CustomEvent(type, {detail})); - } - - declare addEventListener: ( - type: K, - listener: EventListener, - options?: boolean | AddEventListenerOptions - ) => void; - - declare removeEventListener: ( - type: K, - listener: EventListener, - options?: boolean | AddEventListenerOptions - ) => void; - - declare dispatchEvent: ( - event: K extends keyof M ? M[K] : CustomEvent - ) => boolean; -} diff --git a/assets/datagrid/datagrids.ts b/assets/datagrid/datagrids.ts deleted file mode 100644 index 2240727..0000000 --- a/assets/datagrid/datagrids.ts +++ /dev/null @@ -1,85 +0,0 @@ -import {Datagrid} from "@datagrid/datagrid"; -import { - AutosubmitPlugin, - CheckboxPlugin, - ConfirmPlugin, - HappyPlugin, - InlinePlugin, - UrlPlugin, - SortablePlugin, - NetteFormsPlugin, - SelectpickerPlugin -} from "@datagrid/plugins"; -import {Ajax, DatagridsOptions} from "@datagrid/types"; -import {SortableJS} from "@datagrid/integrations/sortable-js"; -import {DatepickerPlugin} from "@datagrid/plugins/integrations/datepicker"; -import {BootstrapSelect, Happy, VanillaDatepicker} from "@datagrid/integrations"; - -export class Datagrids { - private datagrids: Datagrid[] = []; - - readonly options: DatagridsOptions; - - readonly root: HTMLElement; - - constructor(readonly ajax: Ajax, options: Partial = {}) { - this.options = { - selector: "div.datagrid[data-refresh-state]", - datagrid: {}, - root: document.body, - ...options, - }; - - const root = typeof this.options.root === "string" - ? document.querySelector(this.options.root) - : this.options.root; - - if (!root || !(root instanceof HTMLElement)) { - throw new Error("Root element not found or is not an HTMLElement"); - } - - this.root = root; - - this.init(); - } - - init() { - this.ajax.onInit(); - (this.options.datagrid?.plugins ?? []).forEach((plugin) => plugin.onInit?.(this)); - - this.initDatagrids(); - } - - initDatagrids() { - this.datagrids = Array.from(this.root.querySelectorAll(this.options.selector)).map( - datagrid => new Datagrid(datagrid, this.ajax, this.options.datagrid) - ); - } -} - -export const createDatagrids = (ajax: Ajax, _options: Partial = {}) => { - return new Datagrids(ajax, _options); -}; - -/** - * @deprecated Include plugins manually with createDatagrids - */ -export const createFullDatagrids = (ajax: Ajax, _options: Partial = {}) => { - return createDatagrids(ajax, { - datagrid: { - plugins: [ - new AutosubmitPlugin(), - new CheckboxPlugin(), - new ConfirmPlugin(), - new InlinePlugin(), - // new UrlPlugin(), - new NetteFormsPlugin(), - new HappyPlugin(new Happy()), - new SortablePlugin(new SortableJS()), - new DatepickerPlugin(new VanillaDatepicker()), - new SelectpickerPlugin(new BootstrapSelect()) - ], - }, - ..._options, - }) -}; diff --git a/assets/datagrid/index.ts b/assets/datagrid/index.ts deleted file mode 100644 index 39d8538..0000000 --- a/assets/datagrid/index.ts +++ /dev/null @@ -1,6 +0,0 @@ -export * from "./datagrid"; -export * from "./plugins"; -export * from "./integrations"; - -export * from "./datagrids" -export * from "./datagrid"; diff --git a/assets/datagrid/integrations/bootstrap-select.ts b/assets/datagrid/integrations/bootstrap-select.ts deleted file mode 100644 index 28dc39c..0000000 --- a/assets/datagrid/integrations/bootstrap-select.ts +++ /dev/null @@ -1,46 +0,0 @@ -import {Selectpicker} from "@datagrid/types"; -import {window} from "@datagrid/utils"; - -/** - * @deprecated subject for replacement & removal - */ -export class BootstrapSelect implements Selectpicker { - initSelectpickers(elements: HTMLElement[]): void { - if (window().jQuery) { - const $ = window().jQuery; - if ($?.fn.selectpicker) { - $.fn.selectpicker.defaults = { - countSelectedText: elements[0].getAttribute("i18n-selected") ?? "", - iconBase: "fa", - tickIcon: elements[0].getAttribute("selected-icon-check") ?? "fa fa-check", - }; - - elements.forEach(element => - $(element) - .removeClass("form-select form-select-sm") - .addClass("form-control form-control-sm") - .selectpicker("destroy") - .selectpicker({}) - ); - - Array.from(elements) - .filter(element => element.hasAttribute("data-datagrid-multiselect-id")) - .forEach(element => { - const $picker = $(element); - const $parent = $picker.parent(); - - $picker.removeAttr("id"); - const id = element.getAttribute("data-datagrid-multiselect-id"); - - $picker.on("loaded.bs.select", () => { - $parent.attr("style", "display: none;"); - $parent.find(".hidden").removeClass("hidden").addClass("btn-default btn-secondary"); - }); - - $picker.on("rendered.bs.select", () => $parent.attr("id", id)); - }); - } - } - } - -} diff --git a/assets/datagrid/integrations/happy.ts b/assets/datagrid/integrations/happy.ts deleted file mode 100644 index 1c8a755..0000000 --- a/assets/datagrid/integrations/happy.ts +++ /dev/null @@ -1,222 +0,0 @@ -import {happyStyles} from "@datagrid/assets/happy.css"; - -/** - * Slightly cleaned up & typed version of happy-inputs by paveljanda. - */ -export class Happy { - private colors: string[] = ["primary", "success", "info", "warning", "danger", "white", "gray"]; - - private templates = { - radio: '

', - checkbox: - '
', - text: "", - textarea: "", - }; - - init() { - if (!document.querySelector('[data-happy-stylesheet]')) { - document.head.append(``) - } - this.removeBySelector(".happy-radio"); - this.removeBySelector(".happy-checkbox"); - - this.initRadio(); - this.initCheckbox(); - } - - /** - * @deprecated - */ - reset() { - this.init(); - } - - addColorToInput(input: HTMLElement, happyInput: HTMLElement, classString: string) { - if (input.classList.contains(classString)) { - happyInput.classList.add(classString); - } - - classString = `${classString}-border`; - - if (input.classList.contains(classString)) { - happyInput.classList.add(classString); - } - } - - // i... you know what, no, let "thinkess" be "thinkess" - addThinkessToInput(input: HTMLElement, happyInput: HTMLElement) { - if (input.classList.contains("thin")) { - happyInput.classList.add("thin"); - } - } - - setNames(input: HTMLElement, happyInput: HTMLElement) { - happyInput.setAttribute("data-name", input.getAttribute("name") ?? ""); - - var value = input.getAttribute("value"); - - if (value !== "undefined" && value !== null) { - happyInput.setAttribute("data-value", input.getAttribute("value") ?? ""); - } - } - - removeBySelector(selector: string) { - document.querySelectorAll(selector).forEach(el => el.parentNode?.removeChild(el)); - } - - initRadio() { - document.querySelectorAll("input[type=radio].happy").forEach(input => { - /** - * Paste happy component into html - */ - input.insertAdjacentHTML("afterend", this.templates.radio); - - const happyInput = input.nextElementSibling; - - if (happyInput instanceof HTMLElement) { - /** - * Add optional colors - */ - this.colors.forEach(color => { - this.addColorToInput(input, happyInput, color); - this.setNames(input, happyInput); - }); - - this.addThinkessToInput(input, happyInput); - } - - /** - * Init state - */ - this.checkRadioState(input); - - /** - * Set aciton functionality for native change - */ - document.addEventListener("change", this.radioOnChange.bind(this)); - }); - } - - initCheckbox() { - document.querySelectorAll("input[type=checkbox].happy").forEach(input => { - /** - * Paste happy component into html - */ - input.insertAdjacentHTML("afterend", this.templates.checkbox); - - const happyInput = input.nextElementSibling; - - /** - * Add optional colors - */ - if (happyInput instanceof HTMLElement) { - this.colors.forEach(color => { - this.addColorToInput(input, happyInput, color); - this.setNames(input, happyInput); - }); - - this.addThinkessToInput(input, happyInput); - } - - /** - * Init state - */ - this.checkCheckboxState(input); - - /** - * Set action functionality for click || native change - */ - document.addEventListener("click", this.checkCheckboxStateOnClick.bind(this)); - document.addEventListener("change", this.checkCheckboxStateOnChange.bind(this)); - }); - } - - checkCheckboxStateOnClick(event: Event) { - const target = event.target; - - // When target is SVGSVGElement (), return parentNode, - // When target is a SVGGraphicsElement (,...), find and return it's parent node - // otherwise return target itself. - const happyInput = - target instanceof SVGSVGElement - ? target.parentNode - : target instanceof SVGGraphicsElement - ? target.closest("svg")?.parentNode - : target; - - if (!(happyInput instanceof HTMLElement) || !happyInput.classList.contains("happy-checkbox")) { - return; - } - - event.preventDefault(); - - const name = happyInput.getAttribute("data-name"); - const value = happyInput.getAttribute("data-value"); - - const input = document.querySelector( - `.happy-checkbox[data-name="${name}"]` + (!!value ? `[value="${value}"]` : "") - ); - if (!(input instanceof HTMLInputElement)) return; - - const checked = happyInput.classList.contains("active"); - - input.checked = !checked; - checked ? happyInput.classList.remove("active") : happyInput.classList.add("active"); - } - - checkCheckboxStateOnChange({ target }: Event) { - if (!(target instanceof HTMLInputElement)) return; - - if (target.classList.contains("happy")) { - this.checkCheckboxState(target); - } - } - - checkRadioState(input: HTMLInputElement) { - if (!input.checked || !input.hasAttribute("name")) return; - - const name = input.getAttribute("name"); - const value = input.getAttribute("value"); - - const element = document.querySelector( - `.happy-checkbox[data-name="${name}"]` + (!!value ? `[data-value="${value}"]` : "") - ); - - if (element) { - element.classList.add("active"); - } - } - - checkCheckboxState(input: HTMLInputElement) { - const name = input.getAttribute("name"); - if (!name) return; - - const value = input.getAttribute("value"); - const element = document.querySelector( - `.happy-checkbox[data-name="${name}"]` + (!!value ? `[data-value="${value}"]` : "") - ); - - if (!element) return; - - input.checked ? element.classList.add("active") : element.classList.remove("active"); - } - - radioOnChange({ target }: Event) { - // Check whether target is
${snippet}
`; - - childrenBlock.innerHTML = template; - } - //children_block.addClass('loaded'); - //children_block.slideToggle('fast'); - } - } - }) - return true; - } -} \ No newline at end of file diff --git a/assets/datagrid/plugins/index.ts b/assets/datagrid/plugins/index.ts deleted file mode 100644 index 99b83ae..0000000 --- a/assets/datagrid/plugins/index.ts +++ /dev/null @@ -1,12 +0,0 @@ -export * from "./integrations/datepicker"; -export * from "./integrations/happy"; -export * from "./integrations/nette-forms" -export * from "./integrations/selectpicker"; -export * from "./integrations/sortable"; - -export * from "./features/autosubmit"; -export * from "./features/checkboxes"; -export * from "./features/confirm"; -export * from "./features/editable"; -export * from "./features/inline"; -export * from "./features/item-detail"; diff --git a/assets/datagrid/plugins/integrations/datepicker.ts b/assets/datagrid/plugins/integrations/datepicker.ts deleted file mode 100644 index 7e4a1c7..0000000 --- a/assets/datagrid/plugins/integrations/datepicker.ts +++ /dev/null @@ -1,17 +0,0 @@ -import {Datagrid} from "@datagrid"; -import {DatagridPlugin, Datepicker} from "@datagrid/types"; - -export class DatepickerPlugin implements DatagridPlugin { - constructor(private datepicker: Datepicker) { - } - - onDatagridInit(datagrid: Datagrid): boolean { - const elements = datagrid.el.querySelectorAll("input[data-provide='datepicker']"); - - if (elements.length >= 1) { - this.datepicker.initDatepickers(Array.from(elements), datagrid); - } - - return true; - } -} diff --git a/assets/datagrid/plugins/integrations/happy.ts b/assets/datagrid/plugins/integrations/happy.ts deleted file mode 100644 index 32605c0..0000000 --- a/assets/datagrid/plugins/integrations/happy.ts +++ /dev/null @@ -1,19 +0,0 @@ -import {Datagrid} from "@datagrid"; -import { DatagridPlugin } from "@datagrid/types"; -import { window } from "@datagrid/utils"; -import type {Happy} from "@datagrid/integrations"; - -export class HappyPlugin implements DatagridPlugin { - constructor(private happy?: Happy) { - } - - onDatagridInit(datagrid: Datagrid): boolean { - const happy = this.happy ?? window().happy ?? null; - - if (happy) { - happy.init(); - } - - return true; - } -} diff --git a/assets/datagrid/plugins/integrations/nette-forms.ts b/assets/datagrid/plugins/integrations/nette-forms.ts deleted file mode 100644 index 5ffbe75..0000000 --- a/assets/datagrid/plugins/integrations/nette-forms.ts +++ /dev/null @@ -1,18 +0,0 @@ -import {DatagridPlugin, Nette} from "@datagrid/types"; -import {Datagrid} from "@datagrid"; -import {window} from "@datagrid/utils"; - -export class NetteFormsPlugin implements DatagridPlugin { - constructor(private nette?: Nette) { - } - - onDatagridInit(datagrid: Datagrid): boolean { - const nette = this.nette ?? window().Nette ?? null; - - if (nette) { - datagrid.el.querySelectorAll("form").forEach(form => nette.initForm(form)); - } - - return true; - } -} diff --git a/assets/datagrid/plugins/integrations/selectpicker.ts b/assets/datagrid/plugins/integrations/selectpicker.ts deleted file mode 100644 index ef63126..0000000 --- a/assets/datagrid/plugins/integrations/selectpicker.ts +++ /dev/null @@ -1,17 +0,0 @@ -import {DatagridPlugin, Selectpicker} from "@datagrid/types"; -import {Datagrid} from "@datagrid"; - -export class SelectpickerPlugin implements DatagridPlugin { - constructor(private selectpicker: Selectpicker) { - } - - onDatagridInit(datagrid: Datagrid): boolean { - const elements = datagrid.el.querySelectorAll(".selectpicker"); - - if (elements.length >= 1) { - this.selectpicker.initSelectpickers(Array.from(elements), datagrid); - } - - return true; - } -} diff --git a/assets/datagrid/plugins/integrations/sortable.ts b/assets/datagrid/plugins/integrations/sortable.ts deleted file mode 100644 index 4b69631..0000000 --- a/assets/datagrid/plugins/integrations/sortable.ts +++ /dev/null @@ -1,62 +0,0 @@ -import {Datagrid} from "@datagrid/datagrid"; -import { DatagridPlugin, Sortable } from "@datagrid/types"; -import {attachSlideToggle} from "@datagrid/utils"; - -export class SortablePlugin implements DatagridPlugin { - constructor(private sortable: Sortable) { - } - - onDatagridInit(datagrid: Datagrid): boolean { - datagrid.ajax.addEventListener('before', (event) => { - // TODO old ln 694... wtf? - }) - - this.sortable.initSortable(datagrid); - - datagrid.ajax.addEventListener('success', ({detail: {payload}}) => { - if (payload._datagrid_sort) { - for (const key in payload._datagrid_sort) { - const href = payload._datagrid_sort[key]; - const element = datagrid.el.querySelector(`#datagrid-sort-${key}`); - - if (element) { - // TODO: Only for BC support, to be removed - element.setAttribute("href", href); - - element.setAttribute("data-href", href); - } - } - this.sortable.initSortable(datagrid); - } - - if (payload._datagrid_tree) { - const childrenContainer = datagrid.el.querySelector( - `.datagrid-tree-item[data-id='${payload._datagrid_tree}'] .datagrid-tree-item-children` - ); - if (childrenContainer && payload.snippets) { - childrenContainer.classList.add("loaded"); - for (const key in payload.snippets) { - const snippet = payload.snippets[key]; - - const doc = new DOMParser().parseFromString(snippet, 'text/html'); - const element = doc.firstElementChild; - if (element) { - const treeItem = document.createElement("div"); - treeItem.id = key; - treeItem.classList.add("datagrid-tree-item") - treeItem.setAttribute("data-id", key); - if (element.hasAttribute("has-children")) { - treeItem.classList.add("has-children"); - } - - childrenContainer.append(treeItem); - // attachSlideToggle(childrenContainer); - } - } - } - this.sortable.initSortableTree(datagrid); - } - }) - return true; - } -} diff --git a/assets/datagrid/types/ajax.d.ts b/assets/datagrid/types/ajax.d.ts deleted file mode 100644 index 3262f37..0000000 --- a/assets/datagrid/types/ajax.d.ts +++ /dev/null @@ -1,136 +0,0 @@ -import {EventDetail, EventListener, EventMap} from "."; -import {Datagrid} from "@datagrid"; - -export interface BaseRequestParams { - method: "GET" | "HEAD" | "POST" | "PUT" | "DELETE" | "CONNECT" | "OPTIONS" | "TRACE" | "PATCH" | string; - url: string; -} - -export interface RequestParams extends BaseRequestParams { - data: D; -} - -export interface DatagridPayload { - _datagrid_name?: string; - _datagrid_toggle_detail?: string - _datagrid_inline_editing?: boolean; - _datagrid_inline_adding?: boolean; - _datagrid_inline_edited?: boolean; - _datagrid_inline_edit_cancel?: boolean; - _datagrid_url?: boolean; - _datagrid_sort?: Record; - _datagrid_tree?: string; - _datagrid_editable_new_value?: string; - _datagrid_redraw_item_id?: string; - _datagrid_redraw_item_class?: string; - _datagrid_init?: boolean; - non_empty_filters?: string[]; -} - -export interface DatagridState { - "grid-page": number | null, - "grid-perPage": number, - // TODO - "grid-sort": any | null, - "grid-filter": any | null -} - -export type Payload

= P & { - snippets?: Record; - redirect?: string; - state: S; -}; - -export interface Response { - headers: Record | Headers; - status: number; -} - -export interface BeforeEventDetail { - params: RequestParams; -} - -export interface InteractEventDetail { - element: E; -} - -export interface SuccessEventDetail

{ - params: BaseRequestParams; - payload: Payload

; - response: Response; -} - -export interface ErrorEventDetail { - params: BaseRequestParams; - response?: Response; - error?: E; -} - -export interface AjaxEventMap extends EventMap { - before: CustomEvent; - interact: CustomEvent; - snippetUpdate: CustomEvent; - success: CustomEvent; - error: CustomEvent; -} - -export interface Ajax extends EventTarget { - client: C; - - /** - * Initialization of the Ajax instance, called in createDatagrids(). - * @return this - */ - onInit(): this; - - /** - * Initializes a Datagrid instance. - * @param grid The Datagrid instance - */ - onDatagridInit?(grid: G): void; - - /** - * Sends a request to the server. - */ - request(args: RequestParams): Promise

; - - /** - * Submits a form - */ - submitForm(element: E): Promise

; - - /** - * Shortcut for dispatchEvent - * @internal - */ - dispatch( - type: K, - detail: K extends keyof M ? EventDetail : any, - options?: boolean - ): boolean; - - /** - * Note: For events dispatched directly from the underlying client, {@see Ajax.client}} - **/ - addEventListener( - type: K, - listener: EventListener, - options?: boolean | AddEventListenerOptions - ): void; - - /** - * Note: For events dispatched directly from the underlying client, {@see Ajax.client}} - **/ - removeEventListener( - type: K, - listener: EventListener, - options?: boolean | AddEventListenerOptions - ): void; - - /** - * @internal - */ - dispatchEvent( - event: K extends keyof M ? M[K] : CustomEvent - ): boolean; -} diff --git a/assets/datagrid/types/datagrid.d.ts b/assets/datagrid/types/datagrid.d.ts deleted file mode 100644 index 84e99b2..0000000 --- a/assets/datagrid/types/datagrid.d.ts +++ /dev/null @@ -1,29 +0,0 @@ -import {Datagrid, Datagrids} from "@datagrid"; -import {EventMap, Nette} from "@datagrid/types"; - -export interface DatagridEventDetail { - datagrid: Datagrid; -} - -export interface DatagridEventMap extends EventMap { - beforeInit: CustomEvent; - afterInit: CustomEvent; -} - -export interface DatagridPlugin { - onInit?(datagrids: Datagrids): void; - onDatagridInit?(datagrid: Datagrid): boolean; -} - -export interface DatagridOptions { - confirm(this: Datagrid, message: string): boolean; - // Returning null will skip this datagrid - resolveDatagridName: (this: Datagrid, datagrid: HTMLElement) => string | null; - plugins: DatagridPlugin[]; -} - -export interface DatagridsOptions { - datagrid: Partial; - selector: string; - root: HTMLElement | string; -} diff --git a/assets/datagrid/types/index.d.ts b/assets/datagrid/types/index.d.ts deleted file mode 100644 index 39a6073..0000000 --- a/assets/datagrid/types/index.d.ts +++ /dev/null @@ -1,40 +0,0 @@ -import { Happy } from "@datagrid/integrations"; -import TomSelect from "tom-select"; - -export interface Nette { - initForm: (form: HTMLFormElement) => void; -} - -export type Constructor = new (...args: any[]) => T; - -export type KeysOf = { [P in keyof T]: TVal; } - -export interface ExtendedWindow extends Window { - jQuery?: any; - Nette?: Nette; - TomSelect?: Constructor; - happy?: Happy; -} - -// https://github.com/naja-js/naja/blob/384d298a9199bf778985d1bcf5747fe8de305b22/src/utils.ts -type EventListenerFunction = ( - this: ET, - event: E -) => boolean | void | Promise; - -interface EventListenerObject { - handleEvent(event: E): void | Promise; -} - -export type EventListener = - | EventListenerFunction - | EventListenerObject - | null; - -export type EventDetail = E extends CustomEvent ? D : never; - -export interface EventMap extends Record {} - -export * from "./datagrid"; -export * from "./integrations"; -export * from "./ajax"; diff --git a/assets/datagrid/types/integrations.d.ts b/assets/datagrid/types/integrations.d.ts deleted file mode 100644 index 16e7edd..0000000 --- a/assets/datagrid/types/integrations.d.ts +++ /dev/null @@ -1,14 +0,0 @@ -import {Datagrid} from "@datagrid"; - -export interface Sortable { - initSortable(datagrid: Datagrid): void; - initSortableTree(datagrid: Datagrid): void; -} - -export interface Selectpicker { - initSelectpickers(elements: HTMLElement[], datagrid: Datagrid): void; -} - -export interface Datepicker { - initDatepickers(elements: HTMLInputElement[], datagrid: Datagrid): void; -} diff --git a/assets/datagrid/utils.ts b/assets/datagrid/utils.ts deleted file mode 100644 index a4c3b98..0000000 --- a/assets/datagrid/utils.ts +++ /dev/null @@ -1,180 +0,0 @@ -import { Datagrid } from "@datagrid/datagrid"; -import { ExtendedWindow } from "@datagrid/types"; - -export function isPromise(p: any): p is Promise { - return typeof p === "object" && typeof p.then === "function"; -} - -export function isInKeyRange(e: KeyboardEvent, min: number, max: number): boolean { - const code = e.key.length === 1 ? e.key.charCodeAt(0) : 0; - return code >= min && code <= max; -} - -export function isEnter(e: KeyboardEvent): boolean { - return e.key === "Enter"; -} - -export function isEsc(e: KeyboardEvent): boolean { - return e.key === "Escape"; -} - -export function isFunctionKey(e: KeyboardEvent): boolean { - return e.key.length === 2 && e.key.startsWith("F"); -} - -export function window(): ExtendedWindow { - return (window ?? {}) as unknown as ExtendedWindow; -} - -export function slideDown(element: HTMLElement, cb?: (nextStateShown: boolean) => unknown) { - element.style.height = 'auto'; - - let height = element.clientHeight + "px"; - - element.style.height = '0px'; - - setTimeout(function () { - element.style.height = height; - cb?.(true); - }, 0); -} - -export function slideUp(element: HTMLElement, cb?: (nextStateShown: boolean) => unknown) { - element.style.height = '0px'; - - setTimeout( () => { - cb?.(false); - }, 250); // TODO -} - -export function slideToggle(element: HTMLElement, isVisible: boolean, cb?: (nextStateShown: boolean) => unknown) { - console.log("element", element); - if (!isVisible) { - slideDown(element, cb); - } else { - slideUp(element, cb); - } -} - -export function attachSlideToggle(element: HTMLElement, control: HTMLElement, cb?: (nextStateShown: boolean) => unknown) { - if (!control.classList.contains("datagrid--slide-toggle")) { - let sliding = false; - control.classList.add("datagrid--slide-toggle"); - - slideDown(element, cb); - - control.addEventListener('click', () => { - if (sliding) return; - sliding = true; - slideToggle(element, control.classList.contains('is-active'), (active) => { - sliding = false - if (active) { - control.classList.add("is-active"); - } else { - control.classList.remove("is-active"); - } - }); - }); - } -} - -export function qs(params: Record, prefix: string = ""): string { - const encodedParams = []; - - for (const _key in params) { - const value = params[_key]; - // Cannot do !value as that would also exclude valid negative values such as 0 or false - if (value === null || value === undefined) continue; - - const key = prefix ? `${prefix}[${_key}]` : _key; - - // Skip empty strings - if (typeof value === "string" && value.trim().length < 1) continue; - - if (typeof value === "object") { - const nestedParams = qs(value, key); - // Don't include if object is empty - if (nestedParams.length >= 1) { - encodedParams.push(nestedParams); - } - - continue; - } - - encodedParams.push(`${encodeURIComponent(key)}=${encodeURIComponent(value)}`) - } - - return encodedParams.join("&").replace(/&+$/gm, "").replace(/&*$/, ""); -} - -export function calculateCellLines(el: HTMLElement) { - const cellPadding = el.style.padding ? parseInt(el.style.padding.replace(/[^-\d\.]/g, ""), 10) : 0; - const cellHeight = el.getBoundingClientRect().height; - const lineHeight = Math.round(parseFloat(el.style.lineHeight ?? "0")); - const cellLines = Math.round((cellHeight - 2 * cellPadding) / lineHeight); - - return cellLines; -} - -// A little better debounce ;) -export function debounce unknown | Promise>( - fn: TFun, - slowdown: number = 200 -): (...args: TArgs[]) => void { - let timeout: number | null = null; - let blockedByPromise: boolean = false; - - return (...args) => { - if (blockedByPromise) return; - - timeout && clearTimeout(timeout); - timeout = setTimeout(() => { - const result = fn(...args); - - if (isPromise(result)) { - blockedByPromise = true; - result.finally(() => { - blockedByPromise = false; - }); - } - }, slowdown); - }; -} - -export function defaultDatagridNameResolver(this: Datagrid, datagrid: HTMLElement) { - // This attribute is not present by default, though if you're going to use this library - // it's recommended to add it, because when not present, the fallback way is to parse the datagrid- class, - // which is definitely far from reliable. Alternatively (mainly in case of a custom datagrid class), - // you can pass your own resolveDatagridName function to the option. - const attrName = datagrid.getAttribute("data-datagrid-name"); - if (attrName) return attrName; - - console.warn( - "Deprecated name resolution for datagrid", - datagrid, - ": Please add a data-datagrid-name attribute instead!\n" + - "Currently, the Datagrid library relies on matching the name from the 'datagrid-[name]' class, which is unreliable " + - "and may cause bugs if the default class names are not used (eg. if you add a datagrid-xx class, or change the name class completely!)\n" + - "Alternatively, you can customize the name resolution with the `resolveDatagridName` option. See TBD for more info." // TODO - ); - - const classes = datagrid.classList.value.split(" "); - - // Returns the first datagrid-XXX match - for (const className of classes) { - if (!className.startsWith("datagrid-")) continue; - - const [, ...split] = className.split("-"); - const name = split.join("-"); - - // In case nothing actually follows the prefix (className = "datagrid-") - if (name.length < 1) { - console.error(`Failed to resolve datagrid name - ambigious class name '${className}'`); - return null; - } - - return name; - } - - return null; -} diff --git a/assets/js/main.js b/assets/js/main.js index 965a642..303c6c9 100644 --- a/assets/js/main.js +++ b/assets/js/main.js @@ -2,24 +2,26 @@ import naja from "naja"; import netteForms from "nette-forms"; import { AutosubmitPlugin, - BootstrapSelect, CheckboxPlugin, ConfirmPlugin, createDatagrids, + DatepickerPlugin, Happy, HappyPlugin, InlinePlugin, + ItemDetailPlugin, NetteFormsPlugin, SelectpickerPlugin, - DatepickerPlugin, SortableJS, - SortablePlugin, TomSelect, - UrlPlugin, - VanillaDatepicker, ItemDetailPlugin -} from "@datagrid"; -import {NajaAjax} from "@datagrid/ajax"; + SortablePlugin, + TomSelect, + TreeViewPlugin, + VanillaDatepicker +} from "@contributte/datagrid/assets"; +import { NajaAjax } from "@contributte/datagrid/assets/ajax"; import Select from "tom-select"; -import {Dropdown} from "bootstrap"; +import { Dropdown } from "bootstrap"; + // Code highlighting import Prism from "prismjs/components/prism-core"; import "prismjs/components/prism-markup-templating"; @@ -27,18 +29,21 @@ import "prismjs/components/prism-php"; import "prismjs/components/prism-clike"; import "prismjs/components/prism-javascript"; import "prismjs/components/prism-css"; -// Styles +// Styles import '../css/main.css'; -import { TreeViewPlugin } from "../datagrid/plugins/features/treeView"; +// Datagrid + UI document.addEventListener("DOMContentLoaded", () => { - // AJAX - naja.formsHandler.netteForms = netteForms; - + // Initialize dropdowns Array.from(document.querySelectorAll('.dropdown')) .forEach(el => new Dropdown(el)) + // Initialize Naja (nette ajax) + naja.formsHandler.netteForms = netteForms; + naja.initialize(); + + // Initialize datagrids createDatagrids(new NajaAjax(naja), { datagrid: { plugins: [ @@ -47,7 +52,6 @@ document.addEventListener("DOMContentLoaded", () => { new ConfirmPlugin(), new InlinePlugin(), new ItemDetailPlugin(), - // new UrlPlugin(), new NetteFormsPlugin(netteForms), new HappyPlugin(new Happy()), new SortablePlugin(new SortableJS()), @@ -57,9 +61,9 @@ document.addEventListener("DOMContentLoaded", () => { ], }, }); +}); - naja.initialize(); - +document.addEventListener("DOMContentLoaded", () => { // Highlighting const codes = document.querySelectorAll('code'); codes.forEach(code => { diff --git a/package-lock.json b/package-lock.json index f7fc1c1..8ac12de 100644 --- a/package-lock.json +++ b/package-lock.json @@ -9,6 +9,7 @@ "version": "0.0.0", "license": "MIT", "dependencies": { + "@contributte/datagrid": "github:contributte/datagrid#next", "@fortawesome/fontawesome-free": "^6.3.0", "bootstrap": "^5.3.0-alpha3", "naja": "^2.5.0", @@ -34,9 +35,9 @@ } }, "node_modules/@babel/runtime": { - "version": "7.20.13", - "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.20.13.tgz", - "integrity": "sha512-gt3PKXs0DBoL9xCvOIIZ2NEqAGZqHjAnmVbfQtB620V0uReIQutpel14KcneZuer7UioY8ALKZ7iocavvzTNFA==", + "version": "7.22.3", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.22.3.tgz", + "integrity": "sha512-XsDuspWKLUsxwCp6r7EhsExHtYfbe5oAGQ19kqngTdCPUoPQzOPdUbD/pB9PJiwb2ptYKQDjSJT3R6dC+EPqfQ==", "dependencies": { "regenerator-runtime": "^0.13.11" }, @@ -44,6 +45,14 @@ "node": ">=6.9.0" } }, + "node_modules/@contributte/datagrid": { + "version": "6.9.1", + "resolved": "git+ssh://git@github.com/contributte/datagrid.git#dca24b45dd760af0a8c28fd0eb0c45a5d39a7246", + "license": "MIT", + "dependencies": { + "naja": "^2.5.0" + } + }, "node_modules/@esbuild/linux-loong64": { "version": "0.14.54", "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.14.54.tgz", @@ -61,9 +70,9 @@ } }, "node_modules/@fortawesome/fontawesome-free": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/@fortawesome/fontawesome-free/-/fontawesome-free-6.3.0.tgz", - "integrity": "sha512-qVtd5i1Cc7cdrqnTWqTObKQHjPWAiRwjUPaXObaeNPcy7+WKxJumGBx66rfSFgK6LNpIasVKkEgW8oyf0tmPLA==", + "version": "6.4.0", + "resolved": "https://registry.npmjs.org/@fortawesome/fontawesome-free/-/fontawesome-free-6.4.0.tgz", + "integrity": "sha512-0NyytTlPJwB/BF5LtRV8rrABDbe3TdTXqNB3PdZ+UUUZAEIrdOJdmABqKjt4AXwIoJNaRVVZEXxpNrqvE1GAYQ==", "hasInstallScript": true, "engines": { "node": ">=6" @@ -83,9 +92,9 @@ "integrity": "sha512-NvVBRnZNE+dugiXERFsET1JlKZfM5lJDEpSMilKW4bToYJ7pxf0Zne78xyXB2ny2c2aHfJ6WLnz1AaTNHAmQeQ==" }, "node_modules/@popperjs/core": { - "version": "2.11.7", - "resolved": "https://registry.npmjs.org/@popperjs/core/-/core-2.11.7.tgz", - "integrity": "sha512-Cr4OjIkipTtcXKjAsm8agyleBuDHvxzeBoa1v543lbv1YaIwQjESsVcmjiWiPEbC1FIeHOG/Op9kdCmAmiS3Kw==", + "version": "2.11.8", + "resolved": "https://registry.npmjs.org/@popperjs/core/-/core-2.11.8.tgz", + "integrity": "sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A==", "peer": true, "funding": { "type": "opencollective", @@ -111,9 +120,9 @@ } }, "node_modules/@types/jqueryui": { - "version": "1.12.16", - "resolved": "https://registry.npmjs.org/@types/jqueryui/-/jqueryui-1.12.16.tgz", - "integrity": "sha512-6huAQDpNlso9ayaUT9amBOA3kj02OCeUWs+UvDmbaJmwkHSg/HLsQOoap/D5uveN9ePwl72N45Bl+Frp5xyG1Q==", + "version": "1.12.17", + "resolved": "https://registry.npmjs.org/@types/jqueryui/-/jqueryui-1.12.17.tgz", + "integrity": "sha512-rqiCaZO7d1rAcJVXNSV6MYwt42oB4ArTRr0QbU3f4+Siv0d6m9uRkhiKHpc6oL9NFJKDxzIIDvUeMXTtlJFFaA==", "dev": true, "dependencies": { "@types/jquery": "*" @@ -132,15 +141,15 @@ "dev": true }, "node_modules/@types/vanillajs-datepicker": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/@types/vanillajs-datepicker/-/vanillajs-datepicker-1.2.1.tgz", - "integrity": "sha512-j6Rk0IrhuWwztTWcO9mg/fIzVEiqYoOWITI4rGnQiLLsLiaAMqW9E06nfDCBg5HJ94yBn9S7eBFBFC9pJLaiuQ==", + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/@types/vanillajs-datepicker/-/vanillajs-datepicker-1.2.2.tgz", + "integrity": "sha512-jVHa34qqFekNESMk2/ms12DboY4kIyIObQqRM+CFkmrUT4eGtovdqiO//TNIz2N5c9MWdD2/5MQyI7fHfuRzYA==", "dev": true }, "node_modules/autoprefixer": { - "version": "10.4.13", - "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.13.tgz", - "integrity": "sha512-49vKpMqcZYsJjwotvt4+h/BCjJVnhGwcLpDt5xkcaOG3eLrG/HUYLagrihYsQ+qrIBgIzX1Rw7a6L8I/ZA1Atg==", + "version": "10.4.14", + "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.14.tgz", + "integrity": "sha512-FQzyfOsTlwVzjHxKEqRIAdJx9niO6VCBCoEwax/VLSoQF29ggECcPuBqUMZ+u8jCZOPSy8b8/8KnuFbp0SaFZQ==", "dev": true, "funding": [ { @@ -153,8 +162,8 @@ } ], "dependencies": { - "browserslist": "^4.21.4", - "caniuse-lite": "^1.0.30001426", + "browserslist": "^4.21.5", + "caniuse-lite": "^1.0.30001464", "fraction.js": "^4.2.0", "normalize-range": "^0.1.2", "picocolors": "^1.0.0", @@ -171,9 +180,9 @@ } }, "node_modules/bootstrap": { - "version": "5.3.0-alpha3", - "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-5.3.0-alpha3.tgz", - "integrity": "sha512-FBhOWMxkCFr74hesJdchLXhqagPTXS+kRNU3gE0FR5Ki/AdPSz32Ik96Z28+yBluCnE/pc9st7l1yPwKgbtfSA==", + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-5.3.0.tgz", + "integrity": "sha512-UnBV3E3v4STVNQdms6jSGO2CvOkjUMdDAVR2V5N4uCMdaIkaQjbcEAMqRimDHIs4uqBYzDAKCQwCB+97tJgHQw==", "funding": [ { "type": "github", @@ -189,9 +198,9 @@ } }, "node_modules/browserslist": { - "version": "4.21.4", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.21.4.tgz", - "integrity": "sha512-CBHJJdDmgjl3daYjN5Cp5kbTf1mUhZoS+beLklHIvkOWscs83YAhLlF3Wsh/lciQYAcbBJgTOD44VtG31ZM4Hw==", + "version": "4.21.7", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.21.7.tgz", + "integrity": "sha512-BauCXrQ7I2ftSqd2mvKHGo85XR0u7Ru3C/Hxsy/0TkfCtjrmAbPdzLGasmoiBxplpDXlPvdjX9u7srIMfgasNA==", "dev": true, "funding": [ { @@ -201,13 +210,17 @@ { "type": "tidelift", "url": "https://tidelift.com/funding/github/npm/browserslist" + }, + { + "type": "github", + "url": "https://github.com/sponsors/ai" } ], "dependencies": { - "caniuse-lite": "^1.0.30001400", - "electron-to-chromium": "^1.4.251", - "node-releases": "^2.0.6", - "update-browserslist-db": "^1.0.9" + "caniuse-lite": "^1.0.30001489", + "electron-to-chromium": "^1.4.411", + "node-releases": "^2.0.12", + "update-browserslist-db": "^1.0.11" }, "bin": { "browserslist": "cli.js" @@ -217,9 +230,9 @@ } }, "node_modules/caniuse-lite": { - "version": "1.0.30001447", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001447.tgz", - "integrity": "sha512-bdKU1BQDPeEXe9A39xJnGtY0uRq/z5osrnXUw0TcK+EYno45Y+U7QU9HhHEyzvMDffpYadFXi3idnSNkcwLkTw==", + "version": "1.0.30001495", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001495.tgz", + "integrity": "sha512-F6x5IEuigtUfU5ZMQK2jsy5JqUUlEFRVZq8bO2a+ysq5K7jD6PPc9YXZj78xDNS3uNchesp1Jw47YXEqr+Viyg==", "dev": true, "funding": [ { @@ -229,13 +242,17 @@ { "type": "tidelift", "url": "https://tidelift.com/funding/github/npm/caniuse-lite" + }, + { + "type": "github", + "url": "https://github.com/sponsors/ai" } ] }, "node_modules/electron-to-chromium": { - "version": "1.4.284", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.284.tgz", - "integrity": "sha512-M8WEXFuKXMYMVr45fo8mq0wUrrJHheiKZf6BArTKk9ZBYCKJEOU5H8cdWgDT+qCVZf7Na4lVUaZsA+h6uA9+PA==", + "version": "1.4.424", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.424.tgz", + "integrity": "sha512-KOfOIoEE0b3L0CTDgqS+NpokmcBdxpqLIPtp9PL0v5GAMZmZXa9uoUfWJdEy63MNy6jMvKHkBVUYY5DSuqqpdw==", "dev": true }, "node_modules/esbuild": { @@ -649,9 +666,9 @@ } }, "node_modules/is-core-module": { - "version": "2.11.0", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.11.0.tgz", - "integrity": "sha512-RRjxlvLDkD1YJwDbroBHMb+cukurkDWNyHx7D3oNB5x9rb5ogcksMC5wHCadcXoo67gVr/+3GFySh3134zi6rw==", + "version": "2.12.1", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.12.1.tgz", + "integrity": "sha512-Q4ZuBAe2FUsKtyQJoQHlvP8OvBERxO3jEmy1I7hcRXcJBGGHFh/aJBswbXuS9sgrDH2QUO8ilkwNPHvHMd8clg==", "dev": true, "dependencies": { "has": "^1.0.3" @@ -669,10 +686,16 @@ } }, "node_modules/nanoid": { - "version": "3.3.4", - "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.4.tgz", - "integrity": "sha512-MqBkQh/OHTS2egovRtLk45wEyNXwF+cokD+1YPf9u5VfJiRdAiRwB2froX5Co9Rh20xs4siNPm8naNotSD6RBw==", + "version": "3.3.6", + "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.6.tgz", + "integrity": "sha512-BGcqMMJuToF7i1rt+2PWSNVnWIkGCU78jBG3RxO/bZlnZPK2Cmi2QaffxGO/2RvWi9sL+FAiRiXMgsyxQ1DIDA==", "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/ai" + } + ], "bin": { "nanoid": "bin/nanoid.cjs" }, @@ -686,9 +709,9 @@ "integrity": "sha512-UOmA3rF+FjpSci5CGmMtsy79PMWCcl0yyfyCd8YXVS+c68FAnVq3ref5qSxYFcwFynTqcPsYKhsNh8eYW5nVhQ==" }, "node_modules/node-releases": { - "version": "2.0.8", - "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.8.tgz", - "integrity": "sha512-dFSmB8fFHEH/s81Xi+Y/15DQY6VHW81nXRj86EMSL3lmuTmK1e+aT4wrFCkTbm+gSwkw4KpX+rT/pMM2c1mF+A==", + "version": "2.0.12", + "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.12.tgz", + "integrity": "sha512-QzsYKWhXTWx8h1kIvqfnC++o0pEmpRQA/aenALsL2F4pqNVr7YzcdMlDij5WBnwftRbJCNJL/O7zdKaxKPHqgQ==", "dev": true }, "node_modules/normalize-range": { @@ -713,9 +736,9 @@ "dev": true }, "node_modules/postcss": { - "version": "8.4.21", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.21.tgz", - "integrity": "sha512-tP7u/Sn/dVxK2NnruI4H9BG+x+Wxz6oeZ1cJ8P6G/PZY0IKk4k/63TDsQf2kQq3+qoJeLm2kIBUNlZe3zgb4Zg==", + "version": "8.4.24", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.24.tgz", + "integrity": "sha512-M0RzbcI0sO/XJNucsGjvWU9ERWxb/ytp1w6dKtxTKgixdtQDq4rmx/g8W1hnaheq9jgwL/oyEdH5Bc4WwJKMqg==", "dev": true, "funding": [ { @@ -725,10 +748,14 @@ { "type": "tidelift", "url": "https://tidelift.com/funding/github/npm/postcss" + }, + { + "type": "github", + "url": "https://github.com/sponsors/ai" } ], "dependencies": { - "nanoid": "^3.3.4", + "nanoid": "^3.3.6", "picocolors": "^1.0.0", "source-map-js": "^1.0.2" }, @@ -756,12 +783,12 @@ "integrity": "sha512-kY1AZVr2Ra+t+piVaJ4gxaFaReZVH40AKNo7UCX6W+dEwBo/2oZJzqfuN1qLq1oL45o56cPaTXELwrTh8Fpggg==" }, "node_modules/resolve": { - "version": "1.22.1", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.1.tgz", - "integrity": "sha512-nBpuuYuY5jFsli/JIs1oldw6fOQCBioohqWZg/2hiaOybXOft4lonv85uDOKXdf8rhyK159cxU5cDcK/NKk8zw==", + "version": "1.22.2", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.2.tgz", + "integrity": "sha512-Sb+mjNHOULsBv818T40qSPeRiuWLyaGMa5ewydRLFimneixmVy2zdivRl+AF6jaYPC8ERxGDmFSiqui6SfPd+g==", "dev": true, "dependencies": { - "is-core-module": "^2.9.0", + "is-core-module": "^2.11.0", "path-parse": "^1.0.7", "supports-preserve-symlinks-flag": "^1.0.0" }, @@ -843,9 +870,9 @@ } }, "node_modules/update-browserslist-db": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.0.10.tgz", - "integrity": "sha512-OztqDenkfFkbSG+tRxBeAnCVPckDBcvibKd35yDONx6OU8N7sqgwc7rCbkJ/WcYtVRZ4ba68d6byhC21GFh7sQ==", + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.0.11.tgz", + "integrity": "sha512-dCwEFf0/oT85M1fHBg4F0jtLwJrutGoHSQXCh7u4o2t1drG+c0a9Flnqww6XUKSfQMPpJBRjU8d4RXB09qtvaA==", "dev": true, "funding": [ { @@ -855,6 +882,10 @@ { "type": "tidelift", "url": "https://tidelift.com/funding/github/npm/browserslist" + }, + { + "type": "github", + "url": "https://github.com/sponsors/ai" } ], "dependencies": { @@ -862,21 +893,21 @@ "picocolors": "^1.0.0" }, "bin": { - "browserslist-lint": "cli.js" + "update-browserslist-db": "cli.js" }, "peerDependencies": { "browserslist": ">= 4.21.0" } }, "node_modules/vanillajs-datepicker": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/vanillajs-datepicker/-/vanillajs-datepicker-1.3.1.tgz", - "integrity": "sha512-LYYnXXYDw7oqnNbJleLIRXFUjrG2WYOQtU1A2u3FmW3rgzp7lNJ7DGF35CJ3/Dg1OHUh10D9XnJBfSfIKTyeng==" + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/vanillajs-datepicker/-/vanillajs-datepicker-1.3.3.tgz", + "integrity": "sha512-O7eeSSyZ9aeTcy6X9NBswNvWZRRvKIl2F20sbYvL1L32+1fMpiIPD3TvDF4hrU0ezXspHPgGFyvbFkoXIBs83w==" }, "node_modules/vite": { - "version": "2.9.15", - "resolved": "https://registry.npmjs.org/vite/-/vite-2.9.15.tgz", - "integrity": "sha512-fzMt2jK4vQ3yK56te3Kqpkaeq9DkcZfBbzHwYpobasvgYmP2SoAr6Aic05CsB4CzCZbsDv4sujX3pkEGhLabVQ==", + "version": "2.9.16", + "resolved": "https://registry.npmjs.org/vite/-/vite-2.9.16.tgz", + "integrity": "sha512-X+6q8KPyeuBvTQV8AVSnKDvXoBMnTx8zxh54sOwmmuOdxkjMmEJXH2UEchA+vTMps1xw9vL64uwJOWryULg7nA==", "dev": true, "dependencies": { "esbuild": "^0.14.27", diff --git a/package.json b/package.json index 45776c6..ba73ef1 100644 --- a/package.json +++ b/package.json @@ -7,6 +7,7 @@ "node": ">=18.0" }, "dependencies": { + "@contributte/datagrid": "github:contributte/datagrid#next", "@fortawesome/fontawesome-free": "^6.3.0", "bootstrap": "^5.3.0-alpha3", "naja": "^2.5.0", diff --git a/vite.config.js b/vite.config.js index d6fb3ec..ff622c9 100644 --- a/vite.config.js +++ b/vite.config.js @@ -10,7 +10,6 @@ export default defineConfig(({ mode }) => { alias: { '@': resolve(__dirname, 'assets/js'), '~': resolve(__dirname, 'node_modules'), - '@datagrid': resolve(__dirname, 'assets/datagrid'), }, }, base: '/dist/', From 84defdfa08e4f2cd2b7160fe08a887510807337f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Milan=20Felix=20=C5=A0ulc?= Date: Fri, 3 May 2024 21:52:36 +0200 Subject: [PATCH 34/34] Composer: upgrade deps --- composer.lock | 685 +++++++++++++++++++++++--------------------------- 1 file changed, 309 insertions(+), 376 deletions(-) diff --git a/composer.lock b/composer.lock index 454ce4f..7e468eb 100644 --- a/composer.lock +++ b/composer.lock @@ -8,33 +8,32 @@ "packages": [ { "name": "contributte/application", - "version": "v0.5.1", + "version": "v0.5.2", "source": { "type": "git", "url": "https://github.com/contributte/application.git", - "reference": "2579ab2bc3b7c95ae32a2e664ac9a8cc038777f9" + "reference": "f5f8637bd54eacd1cc45792f23bb8831873ddb35" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/contributte/application/zipball/2579ab2bc3b7c95ae32a2e664ac9a8cc038777f9", - "reference": "2579ab2bc3b7c95ae32a2e664ac9a8cc038777f9", + "url": "https://api.github.com/repos/contributte/application/zipball/f5f8637bd54eacd1cc45792f23bb8831873ddb35", + "reference": "f5f8637bd54eacd1cc45792f23bb8831873ddb35", "shasum": "" }, "require": { - "nette/application": "^3.0.0", + "nette/application": "^3.0.0 || ^4.0", "php": ">=7.2" }, "require-dev": { - "nette/http": "~2.4.8 || ~3.0.0", + "nette/http": "~2.4.8 || ^3.0.0", "ninjify/nunjuck": "^0.3.0", - "ninjify/qa": "^0.9.0", - "phpstan/extension-installer": "^1.0", - "phpstan/phpstan-deprecation-rules": "^0.11.0", - "phpstan/phpstan-nette": "^0.11.1", - "phpstan/phpstan-shim": "^0.11.2", - "phpstan/phpstan-strict-rules": "^0.11.0", + "ninjify/qa": "^0.13.0", + "phpstan/phpstan": "^1.0", + "phpstan/phpstan-deprecation-rules": "^1.0", + "phpstan/phpstan-nette": "^1.0", + "phpstan/phpstan-strict-rules": "^1.0", "psr/http-message": "~1.0.1", - "tracy/tracy": "~2.6.1" + "tracy/tracy": "~2.9.1" }, "type": "library", "extra": { @@ -68,7 +67,7 @@ ], "support": { "issues": "https://github.com/contributte/application/issues", - "source": "https://github.com/contributte/application/tree/v0.5.1" + "source": "https://github.com/contributte/application/tree/v0.5.2" }, "funding": [ { @@ -80,7 +79,7 @@ "type": "github" } ], - "time": "2021-03-10T21:48:30+00:00" + "time": "2023-09-27T20:32:37+00:00" }, { "name": "contributte/bootstrap", @@ -146,16 +145,16 @@ }, { "name": "contributte/di", - "version": "v0.5.5", + "version": "v0.5.6", "source": { "type": "git", "url": "https://github.com/contributte/di.git", - "reference": "2857d07b15c8d0136038f4daa6930c42491a6f6a" + "reference": "49d6b93d46f57be319b1e811cd983bfed0c90979" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/contributte/di/zipball/2857d07b15c8d0136038f4daa6930c42491a6f6a", - "reference": "2857d07b15c8d0136038f4daa6930c42491a6f6a", + "url": "https://api.github.com/repos/contributte/di/zipball/49d6b93d46f57be319b1e811cd983bfed0c90979", + "reference": "49d6b93d46f57be319b1e811cd983bfed0c90979", "shasum": "" }, "require": { @@ -206,7 +205,7 @@ ], "support": { "issues": "https://github.com/contributte/di/issues", - "source": "https://github.com/contributte/di/tree/v0.5.5" + "source": "https://github.com/contributte/di/tree/v0.5.6" }, "funding": [ { @@ -218,7 +217,7 @@ "type": "github" } ], - "time": "2023-02-21T08:24:32+00:00" + "time": "2023-09-05T08:23:55+00:00" }, { "name": "contributte/forms", @@ -304,43 +303,36 @@ }, { "name": "contributte/latte", - "version": "dev-master", + "version": "v0.6.0", "source": { "type": "git", "url": "https://github.com/contributte/latte.git", - "reference": "6e11db54b4cf0f4579b58b69150ef74b67a1f414" + "reference": "f558925e5b9e29e669f242fdfd3dcb520652b9c3" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/contributte/latte/zipball/6e11db54b4cf0f4579b58b69150ef74b67a1f414", - "reference": "6e11db54b4cf0f4579b58b69150ef74b67a1f414", + "url": "https://api.github.com/repos/contributte/latte/zipball/f558925e5b9e29e669f242fdfd3dcb520652b9c3", + "reference": "f558925e5b9e29e669f242fdfd3dcb520652b9c3", "shasum": "" }, "require": { - "latte/latte": "^2.5.1 || ^3.0", - "php": ">=7.2" - }, - "conflict": { - "nette/di": "<3.0.0" + "latte/latte": "^3.0.12", + "php": ">=8.1" }, "require-dev": { - "nette/application": "^3.0", - "nette/di": "~3.0.0", - "ninjify/nunjuck": "^0.4", - "ninjify/qa": "^0.12", - "phpstan/phpstan": "^1.0", - "phpstan/phpstan-deprecation-rules": "^1.0", - "phpstan/phpstan-nette": "^1.0", - "phpstan/phpstan-strict-rules": "^1.0" + "contributte/phpstan": "^0.1", + "contributte/qa": "^0.4", + "contributte/tester": "^0.4", + "nette/application": "^3.1.14", + "nette/di": "^3.0.17" }, "suggest": { "nette/di": "to use VersionExtension[CompilerExtension]" }, - "default-branch": true, "type": "library", "extra": { "branch-alias": { - "dev-master": "0.6.x-dev" + "dev-master": "0.7.x-dev" } }, "autoload": { @@ -367,7 +359,7 @@ ], "support": { "issues": "https://github.com/contributte/latte/issues", - "source": "https://github.com/contributte/latte/tree/master" + "source": "https://github.com/contributte/latte/tree/v0.6.0" }, "funding": [ { @@ -379,20 +371,20 @@ "type": "github" } ], - "time": "2023-02-13T16:14:37+00:00" + "time": "2023-12-12T19:43:05+00:00" }, { "name": "contributte/nella", - "version": "dev-master", + "version": "v0.1", "source": { "type": "git", "url": "https://github.com/contributte/nella.git", - "reference": "bdb893fd6be8049d2b728f993ddba8362475e2dc" + "reference": "6a701ac972674aa02adee9abe508f60fe9a082cd" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/contributte/nella/zipball/bdb893fd6be8049d2b728f993ddba8362475e2dc", - "reference": "bdb893fd6be8049d2b728f993ddba8362475e2dc", + "url": "https://api.github.com/repos/contributte/nella/zipball/6a701ac972674aa02adee9abe508f60fe9a082cd", + "reference": "6a701ac972674aa02adee9abe508f60fe9a082cd", "shasum": "" }, "require": { @@ -414,7 +406,6 @@ "phpstan/phpstan-nette": "^1.0.0", "phpstan/phpstan-strict-rules": "^1.1.0" }, - "default-branch": true, "type": "library", "extra": { "branch-alias": { @@ -446,7 +437,7 @@ ], "support": { "issues": "https://github.com/contributte/nella/issues", - "source": "https://github.com/contributte/nella/tree/master" + "source": "https://github.com/contributte/nella/tree/v0.1" }, "funding": [ { @@ -458,7 +449,7 @@ "type": "github" } ], - "time": "2023-03-07T19:43:10+00:00" + "time": "2023-04-29T10:21:45+00:00" }, { "name": "contributte/tracy", @@ -614,16 +605,16 @@ }, { "name": "dibi/dibi", - "version": "v4.2.7", + "version": "v4.2.8", "source": { "type": "git", "url": "https://github.com/dg/dibi.git", - "reference": "7fa05f381b23fdc59af98caeb03b1ae8ed1e03ed" + "reference": "cb0cf4ba2face22d809c8f863a5a0465b46a6ca9" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/dg/dibi/zipball/7fa05f381b23fdc59af98caeb03b1ae8ed1e03ed", - "reference": "7fa05f381b23fdc59af98caeb03b1ae8ed1e03ed", + "url": "https://api.github.com/repos/dg/dibi/zipball/cb0cf4ba2face22d809c8f863a5a0465b46a6ca9", + "reference": "cb0cf4ba2face22d809c8f863a5a0465b46a6ca9", "shasum": "" }, "require": { @@ -678,28 +669,28 @@ ], "support": { "issues": "https://github.com/dg/dibi/issues", - "source": "https://github.com/dg/dibi/tree/v4.2.7" + "source": "https://github.com/dg/dibi/tree/v4.2.8" }, - "time": "2022-11-18T03:40:51+00:00" + "time": "2023-08-09T14:15:07+00:00" }, { "name": "latte/latte", - "version": "v3.0.6", + "version": "v3.0.15", "source": { "type": "git", "url": "https://github.com/nette/latte.git", - "reference": "6f66dcfea7ad76f60b8234139161421e9e1e309f" + "reference": "b4807f2f6ef774adb946da1b174e1e85171a9101" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/latte/zipball/6f66dcfea7ad76f60b8234139161421e9e1e309f", - "reference": "6f66dcfea7ad76f60b8234139161421e9e1e309f", + "url": "https://api.github.com/repos/nette/latte/zipball/b4807f2f6ef774adb946da1b174e1e85171a9101", + "reference": "b4807f2f6ef774adb946da1b174e1e85171a9101", "shasum": "" }, "require": { "ext-json": "*", "ext-tokenizer": "*", - "php": ">=8.0 <8.3" + "php": "8.0 - 8.3" }, "conflict": { "nette/application": "<3.1.7", @@ -763,33 +754,33 @@ ], "support": { "issues": "https://github.com/nette/latte/issues", - "source": "https://github.com/nette/latte/tree/v3.0.6" + "source": "https://github.com/nette/latte/tree/v3.0.15" }, - "time": "2023-03-09T01:34:56+00:00" + "time": "2024-04-30T05:57:23+00:00" }, { "name": "nette/application", - "version": "v3.1.10", + "version": "v3.1.14", "source": { "type": "git", "url": "https://github.com/nette/application.git", - "reference": "9c31b24407623437c1e1345cc2bd4e210b290135" + "reference": "0729ede7e66fad642046a3eb670d368845272573" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/application/zipball/9c31b24407623437c1e1345cc2bd4e210b290135", - "reference": "9c31b24407623437c1e1345cc2bd4e210b290135", + "url": "https://api.github.com/repos/nette/application/zipball/0729ede7e66fad642046a3eb670d368845272573", + "reference": "0729ede7e66fad642046a3eb670d368845272573", "shasum": "" }, "require": { "nette/component-model": "^3.0", "nette/http": "^3.0.2", - "nette/routing": "^3.0.2", + "nette/routing": "^3.0.5", "nette/utils": "^3.2.1 || ~4.0.0", "php": ">=7.2" }, "conflict": { - "latte/latte": "<2.7.1 || >=3.0.0 <3.0.5 || >=3.1", + "latte/latte": "<2.7.1 || >=3.0.0 <3.0.8 || >=3.1", "nette/caching": "<3.1", "nette/di": "<3.0.7", "nette/forms": "<3.0", @@ -855,41 +846,41 @@ ], "support": { "issues": "https://github.com/nette/application/issues", - "source": "https://github.com/nette/application/tree/v3.1.10" + "source": "https://github.com/nette/application/tree/v3.1.14" }, - "time": "2023-01-17T13:52:03+00:00" + "time": "2023-10-09T02:45:43+00:00" }, { "name": "nette/bootstrap", - "version": "v3.2.0", + "version": "v3.2.3", "source": { "type": "git", "url": "https://github.com/nette/bootstrap.git", - "reference": "7fde23cc8a8cf97d545baf0ad7f8cd47c73feb17" + "reference": "5f8b9420b0b5441b55f0745dd0e8afa1653e5e6c" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/bootstrap/zipball/7fde23cc8a8cf97d545baf0ad7f8cd47c73feb17", - "reference": "7fde23cc8a8cf97d545baf0ad7f8cd47c73feb17", + "url": "https://api.github.com/repos/nette/bootstrap/zipball/5f8b9420b0b5441b55f0745dd0e8afa1653e5e6c", + "reference": "5f8b9420b0b5441b55f0745dd0e8afa1653e5e6c", "shasum": "" }, "require": { "nette/di": "^3.1", "nette/utils": "^3.2.1 || ^4.0", - "php": ">=8.0 <8.3" + "php": "8.0 - 8.3" }, "conflict": { "tracy/tracy": "<2.6" }, "require-dev": { - "latte/latte": "^2.8", + "latte/latte": "^2.8 || ^3.0", "nette/application": "^3.1", "nette/caching": "^3.0", "nette/database": "^3.0", "nette/forms": "^3.0", "nette/http": "^3.0", - "nette/mail": "^3.0", - "nette/robot-loader": "^3.0", + "nette/mail": "^3.0 || ^4.0", + "nette/robot-loader": "^3.0 || ^4.0", "nette/safe-stream": "^2.2", "nette/security": "^3.0", "nette/tester": "^2.4", @@ -936,9 +927,9 @@ ], "support": { "issues": "https://github.com/nette/bootstrap/issues", - "source": "https://github.com/nette/bootstrap/tree/v3.2.0" + "source": "https://github.com/nette/bootstrap/tree/v3.2.3" }, - "time": "2023-01-13T04:09:35+00:00" + "time": "2024-04-19T00:07:13+00:00" }, { "name": "nette/component-model", @@ -1004,16 +995,16 @@ }, { "name": "nette/di", - "version": "v3.1.2", + "version": "v3.1.10", "source": { "type": "git", "url": "https://github.com/nette/di.git", - "reference": "355cefbd71011a76b670fda3340d612a6944f972" + "reference": "2645ec3eaa17fa2ab87c5eb4eaacb1fe6dd28284" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/di/zipball/355cefbd71011a76b670fda3340d612a6944f972", - "reference": "355cefbd71011a76b670fda3340d612a6944f972", + "url": "https://api.github.com/repos/nette/di/zipball/2645ec3eaa17fa2ab87c5eb4eaacb1fe6dd28284", + "reference": "2645ec3eaa17fa2ab87c5eb4eaacb1fe6dd28284", "shasum": "" }, "require": { @@ -1021,9 +1012,9 @@ "nette/neon": "^3.3 || ^4.0", "nette/php-generator": "^3.5.4 || ^4.0", "nette/robot-loader": "^3.2 || ~4.0.0", - "nette/schema": "^1.2", + "nette/schema": "^1.2.5", "nette/utils": "^3.2.5 || ~4.0.0", - "php": ">=7.2 <8.3" + "php": "7.2 - 8.3" }, "require-dev": { "nette/tester": "^2.4", @@ -1070,9 +1061,9 @@ ], "support": { "issues": "https://github.com/nette/di/issues", - "source": "https://github.com/nette/di/tree/v3.1.2" + "source": "https://github.com/nette/di/tree/v3.1.10" }, - "time": "2023-03-13T14:03:15+00:00" + "time": "2024-02-06T01:19:44+00:00" }, { "name": "nette/finder", @@ -1143,35 +1134,38 @@ }, { "name": "nette/forms", - "version": "v3.1.11", + "version": "v3.1.15", "source": { "type": "git", "url": "https://github.com/nette/forms.git", - "reference": "64cdc2d6796a8fe1265bb21a6ee5e9ff93e2b3a4" + "reference": "f373bcd5ea7a33672fa96035d4bf3110ab66ee44" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/forms/zipball/64cdc2d6796a8fe1265bb21a6ee5e9ff93e2b3a4", - "reference": "64cdc2d6796a8fe1265bb21a6ee5e9ff93e2b3a4", + "url": "https://api.github.com/repos/nette/forms/zipball/f373bcd5ea7a33672fa96035d4bf3110ab66ee44", + "reference": "f373bcd5ea7a33672fa96035d4bf3110ab66ee44", "shasum": "" }, "require": { "nette/component-model": "^3.0", "nette/http": "^3.1", "nette/utils": "^3.2.5 || ~4.0.0", - "php": ">=7.2 <8.3" + "php": "7.2 - 8.3" }, "conflict": { - "latte/latte": ">=3.1" + "latte/latte": ">=3.0.0 <3.0.12 || >=3.1" }, "require-dev": { - "latte/latte": "^2.10.2 || ^3.0.3", + "latte/latte": "^2.10.2 || ^3.0.12", "nette/application": "^3.0", "nette/di": "^3.0", "nette/tester": "^2.4", "phpstan/phpstan-nette": "^1", "tracy/tracy": "^2.9" }, + "suggest": { + "ext-intl": "to use date/time controls" + }, "type": "library", "extra": { "branch-alias": { @@ -1211,27 +1205,27 @@ ], "support": { "issues": "https://github.com/nette/forms/issues", - "source": "https://github.com/nette/forms/tree/v3.1.11" + "source": "https://github.com/nette/forms/tree/v3.1.15" }, - "time": "2023-03-08T23:56:24+00:00" + "time": "2024-01-21T22:22:16+00:00" }, { "name": "nette/http", - "version": "v3.2.2", + "version": "v3.2.4", "source": { "type": "git", "url": "https://github.com/nette/http.git", - "reference": "9105c26de3dd47da5e7cf6b4132b5d871f835e25" + "reference": "d7cc833ee186d5139cde5aab43b39ee7aedd6f22" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/http/zipball/9105c26de3dd47da5e7cf6b4132b5d871f835e25", - "reference": "9105c26de3dd47da5e7cf6b4132b5d871f835e25", + "url": "https://api.github.com/repos/nette/http/zipball/d7cc833ee186d5139cde5aab43b39ee7aedd6f22", + "reference": "d7cc833ee186d5139cde5aab43b39ee7aedd6f22", "shasum": "" }, "require": { "nette/utils": "^3.2.1 || ~4.0.0", - "php": ">=7.2 <8.3" + "php": "7.2 - 8.3" }, "conflict": { "nette/di": "<3.0.3", @@ -1245,7 +1239,10 @@ "tracy/tracy": "^2.8" }, "suggest": { - "ext-fileinfo": "to detect type of uploaded files" + "ext-fileinfo": "to detect MIME type of uploaded files by Nette\\Http\\FileUpload", + "ext-gd": "to use image function in Nette\\Http\\FileUpload", + "ext-intl": "to support punycode by Nette\\Http\\Url", + "ext-session": "to use Nette\\Http\\Session" }, "type": "library", "extra": { @@ -1289,27 +1286,27 @@ ], "support": { "issues": "https://github.com/nette/http/issues", - "source": "https://github.com/nette/http/tree/v3.2.2" + "source": "https://github.com/nette/http/tree/v3.2.4" }, - "time": "2023-03-18T14:55:56+00:00" + "time": "2024-01-30T18:13:43+00:00" }, { "name": "nette/neon", - "version": "v3.4.0", + "version": "v3.4.1", "source": { "type": "git", "url": "https://github.com/nette/neon.git", - "reference": "372d945c156ee7f35c953339fb164538339e6283" + "reference": "457bfbf0560f600b30d9df4233af382a478bb44d" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/neon/zipball/372d945c156ee7f35c953339fb164538339e6283", - "reference": "372d945c156ee7f35c953339fb164538339e6283", + "url": "https://api.github.com/repos/nette/neon/zipball/457bfbf0560f600b30d9df4233af382a478bb44d", + "reference": "457bfbf0560f600b30d9df4233af382a478bb44d", "shasum": "" }, "require": { "ext-json": "*", - "php": ">=8.0 <8.3" + "php": "8.0 - 8.3" }, "require-dev": { "nette/tester": "^2.4", @@ -1357,32 +1354,32 @@ ], "support": { "issues": "https://github.com/nette/neon/issues", - "source": "https://github.com/nette/neon/tree/v3.4.0" + "source": "https://github.com/nette/neon/tree/v3.4.1" }, - "time": "2023-01-13T03:08:29+00:00" + "time": "2023-09-27T08:59:11+00:00" }, { "name": "nette/php-generator", - "version": "v4.0.6", + "version": "v4.1.4", "source": { "type": "git", "url": "https://github.com/nette/php-generator.git", - "reference": "0f1275bb8d39b3eb92b57c22a51fe693f1f145a5" + "reference": "b135071d8da108445e4df2fc6a75522b23c0237d" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/php-generator/zipball/0f1275bb8d39b3eb92b57c22a51fe693f1f145a5", - "reference": "0f1275bb8d39b3eb92b57c22a51fe693f1f145a5", + "url": "https://api.github.com/repos/nette/php-generator/zipball/b135071d8da108445e4df2fc6a75522b23c0237d", + "reference": "b135071d8da108445e4df2fc6a75522b23c0237d", "shasum": "" }, "require": { "nette/utils": "^3.2.9 || ^4.0", - "php": ">=8.0 <8.3" + "php": "8.0 - 8.3" }, "require-dev": { "jetbrains/phpstorm-attributes": "dev-master", "nette/tester": "^2.4", - "nikic/php-parser": "^4.15", + "nikic/php-parser": "^4.18 || ^5.0", "phpstan/phpstan": "^1.0", "tracy/tracy": "^2.8" }, @@ -1392,7 +1389,7 @@ "type": "library", "extra": { "branch-alias": { - "dev-master": "4.0-dev" + "dev-master": "4.1-dev" } }, "autoload": { @@ -1416,7 +1413,7 @@ "homepage": "https://nette.org/contributors" } ], - "description": "🐘 Nette PHP Generator: generates neat PHP code for you. Supports new PHP 8.2 features.", + "description": "🐘 Nette PHP Generator: generates neat PHP code for you. Supports new PHP 8.3 features.", "homepage": "https://nette.org", "keywords": [ "code", @@ -1426,9 +1423,9 @@ ], "support": { "issues": "https://github.com/nette/php-generator/issues", - "source": "https://github.com/nette/php-generator/tree/v4.0.6" + "source": "https://github.com/nette/php-generator/tree/v4.1.4" }, - "time": "2023-03-13T17:38:30+00:00" + "time": "2024-03-07T23:06:26+00:00" }, { "name": "nette/robot-loader", @@ -1499,16 +1496,16 @@ }, { "name": "nette/routing", - "version": "v3.0.4", + "version": "v3.0.5", "source": { "type": "git", "url": "https://github.com/nette/routing.git", - "reference": "eaefe6375303799366f3e43977daaf33f5f89b95" + "reference": "ff709ff9ed38a14c4fe3472534526593a8461ff5" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/routing/zipball/eaefe6375303799366f3e43977daaf33f5f89b95", - "reference": "eaefe6375303799366f3e43977daaf33f5f89b95", + "url": "https://api.github.com/repos/nette/routing/zipball/ff709ff9ed38a14c4fe3472534526593a8461ff5", + "reference": "ff709ff9ed38a14c4fe3472534526593a8461ff5", "shasum": "" }, "require": { @@ -1555,27 +1552,27 @@ ], "support": { "issues": "https://github.com/nette/routing/issues", - "source": "https://github.com/nette/routing/tree/v3.0.4" + "source": "https://github.com/nette/routing/tree/v3.0.5" }, - "time": "2023-01-18T04:58:41+00:00" + "time": "2023-10-08T21:37:46+00:00" }, { "name": "nette/schema", - "version": "v1.2.3", + "version": "v1.2.5", "source": { "type": "git", "url": "https://github.com/nette/schema.git", - "reference": "abbdbb70e0245d5f3bf77874cea1dfb0c930d06f" + "reference": "0462f0166e823aad657c9224d0f849ecac1ba10a" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/schema/zipball/abbdbb70e0245d5f3bf77874cea1dfb0c930d06f", - "reference": "abbdbb70e0245d5f3bf77874cea1dfb0c930d06f", + "url": "https://api.github.com/repos/nette/schema/zipball/0462f0166e823aad657c9224d0f849ecac1ba10a", + "reference": "0462f0166e823aad657c9224d0f849ecac1ba10a", "shasum": "" }, "require": { "nette/utils": "^2.5.7 || ^3.1.5 || ^4.0", - "php": ">=7.1 <8.3" + "php": "7.1 - 8.3" }, "require-dev": { "nette/tester": "^2.3 || ^2.4", @@ -1617,26 +1614,26 @@ ], "support": { "issues": "https://github.com/nette/schema/issues", - "source": "https://github.com/nette/schema/tree/v1.2.3" + "source": "https://github.com/nette/schema/tree/v1.2.5" }, - "time": "2022-10-13T01:24:26+00:00" + "time": "2023-10-05T20:37:59+00:00" }, { "name": "nette/utils", - "version": "v3.2.9", + "version": "v3.2.10", "source": { "type": "git", "url": "https://github.com/nette/utils.git", - "reference": "c91bac3470c34b2ecd5400f6e6fdf0b64a836a5c" + "reference": "a4175c62652f2300c8017fb7e640f9ccb11648d2" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/utils/zipball/c91bac3470c34b2ecd5400f6e6fdf0b64a836a5c", - "reference": "c91bac3470c34b2ecd5400f6e6fdf0b64a836a5c", + "url": "https://api.github.com/repos/nette/utils/zipball/a4175c62652f2300c8017fb7e640f9ccb11648d2", + "reference": "a4175c62652f2300c8017fb7e640f9ccb11648d2", "shasum": "" }, "require": { - "php": ">=7.2 <8.3" + "php": ">=7.2 <8.4" }, "conflict": { "nette/di": "<3.0.6" @@ -1703,89 +1700,22 @@ ], "support": { "issues": "https://github.com/nette/utils/issues", - "source": "https://github.com/nette/utils/tree/v3.2.9" - }, - "time": "2023-01-18T03:26:20+00:00" - }, - { - "name": "symfony/deprecation-contracts", - "version": "v3.2.1", - "source": { - "type": "git", - "url": "https://github.com/symfony/deprecation-contracts.git", - "reference": "e2d1534420bd723d0ef5aec58a22c5fe60ce6f5e" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/e2d1534420bd723d0ef5aec58a22c5fe60ce6f5e", - "reference": "e2d1534420bd723d0ef5aec58a22c5fe60ce6f5e", - "shasum": "" - }, - "require": { - "php": ">=8.1" - }, - "type": "library", - "extra": { - "branch-alias": { - "dev-main": "3.3-dev" - }, - "thanks": { - "name": "symfony/contracts", - "url": "https://github.com/symfony/contracts" - } - }, - "autoload": { - "files": [ - "function.php" - ] - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "MIT" - ], - "authors": [ - { - "name": "Nicolas Grekas", - "email": "p@tchwork.com" - }, - { - "name": "Symfony Community", - "homepage": "https://symfony.com/contributors" - } - ], - "description": "A generic function and convention to trigger deprecation notices", - "homepage": "https://symfony.com", - "support": { - "source": "https://github.com/symfony/deprecation-contracts/tree/v3.2.1" + "source": "https://github.com/nette/utils/tree/v3.2.10" }, - "funding": [ - { - "url": "https://symfony.com/sponsor", - "type": "custom" - }, - { - "url": "https://github.com/fabpot", - "type": "github" - }, - { - "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", - "type": "tidelift" - } - ], - "time": "2023-03-01T10:25:55+00:00" + "time": "2023-07-30T15:38:18+00:00" }, { "name": "symfony/polyfill-ctype", - "version": "v1.27.0", + "version": "v1.29.0", "source": { "type": "git", "url": "https://github.com/symfony/polyfill-ctype.git", - "reference": "5bbc823adecdae860bb64756d639ecfec17b050a" + "reference": "ef4d7e442ca910c4764bce785146269b30cb5fc4" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/5bbc823adecdae860bb64756d639ecfec17b050a", - "reference": "5bbc823adecdae860bb64756d639ecfec17b050a", + "url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/ef4d7e442ca910c4764bce785146269b30cb5fc4", + "reference": "ef4d7e442ca910c4764bce785146269b30cb5fc4", "shasum": "" }, "require": { @@ -1799,9 +1729,6 @@ }, "type": "library", "extra": { - "branch-alias": { - "dev-main": "1.27-dev" - }, "thanks": { "name": "symfony/polyfill", "url": "https://github.com/symfony/polyfill" @@ -1838,7 +1765,7 @@ "portable" ], "support": { - "source": "https://github.com/symfony/polyfill-ctype/tree/v1.27.0" + "source": "https://github.com/symfony/polyfill-ctype/tree/v1.29.0" }, "funding": [ { @@ -1854,20 +1781,20 @@ "type": "tidelift" } ], - "time": "2022-11-03T14:55:06+00:00" + "time": "2024-01-29T20:11:03+00:00" }, { "name": "symfony/polyfill-intl-grapheme", - "version": "v1.27.0", + "version": "v1.29.0", "source": { "type": "git", "url": "https://github.com/symfony/polyfill-intl-grapheme.git", - "reference": "511a08c03c1960e08a883f4cffcacd219b758354" + "reference": "32a9da87d7b3245e09ac426c83d334ae9f06f80f" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/511a08c03c1960e08a883f4cffcacd219b758354", - "reference": "511a08c03c1960e08a883f4cffcacd219b758354", + "url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/32a9da87d7b3245e09ac426c83d334ae9f06f80f", + "reference": "32a9da87d7b3245e09ac426c83d334ae9f06f80f", "shasum": "" }, "require": { @@ -1878,9 +1805,6 @@ }, "type": "library", "extra": { - "branch-alias": { - "dev-main": "1.27-dev" - }, "thanks": { "name": "symfony/polyfill", "url": "https://github.com/symfony/polyfill" @@ -1919,7 +1843,7 @@ "shim" ], "support": { - "source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.27.0" + "source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.29.0" }, "funding": [ { @@ -1935,20 +1859,20 @@ "type": "tidelift" } ], - "time": "2022-11-03T14:55:06+00:00" + "time": "2024-01-29T20:11:03+00:00" }, { "name": "symfony/polyfill-intl-normalizer", - "version": "v1.27.0", + "version": "v1.29.0", "source": { "type": "git", "url": "https://github.com/symfony/polyfill-intl-normalizer.git", - "reference": "19bd1e4fcd5b91116f14d8533c57831ed00571b6" + "reference": "bc45c394692b948b4d383a08d7753968bed9a83d" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/polyfill-intl-normalizer/zipball/19bd1e4fcd5b91116f14d8533c57831ed00571b6", - "reference": "19bd1e4fcd5b91116f14d8533c57831ed00571b6", + "url": "https://api.github.com/repos/symfony/polyfill-intl-normalizer/zipball/bc45c394692b948b4d383a08d7753968bed9a83d", + "reference": "bc45c394692b948b4d383a08d7753968bed9a83d", "shasum": "" }, "require": { @@ -1959,9 +1883,6 @@ }, "type": "library", "extra": { - "branch-alias": { - "dev-main": "1.27-dev" - }, "thanks": { "name": "symfony/polyfill", "url": "https://github.com/symfony/polyfill" @@ -2003,7 +1924,7 @@ "shim" ], "support": { - "source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.27.0" + "source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.29.0" }, "funding": [ { @@ -2019,20 +1940,20 @@ "type": "tidelift" } ], - "time": "2022-11-03T14:55:06+00:00" + "time": "2024-01-29T20:11:03+00:00" }, { "name": "symfony/polyfill-mbstring", - "version": "v1.27.0", + "version": "v1.29.0", "source": { "type": "git", "url": "https://github.com/symfony/polyfill-mbstring.git", - "reference": "8ad114f6b39e2c98a8b0e3bd907732c207c2b534" + "reference": "9773676c8a1bb1f8d4340a62efe641cf76eda7ec" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/8ad114f6b39e2c98a8b0e3bd907732c207c2b534", - "reference": "8ad114f6b39e2c98a8b0e3bd907732c207c2b534", + "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/9773676c8a1bb1f8d4340a62efe641cf76eda7ec", + "reference": "9773676c8a1bb1f8d4340a62efe641cf76eda7ec", "shasum": "" }, "require": { @@ -2046,9 +1967,6 @@ }, "type": "library", "extra": { - "branch-alias": { - "dev-main": "1.27-dev" - }, "thanks": { "name": "symfony/polyfill", "url": "https://github.com/symfony/polyfill" @@ -2086,7 +2004,7 @@ "shim" ], "support": { - "source": "https://github.com/symfony/polyfill-mbstring/tree/v1.27.0" + "source": "https://github.com/symfony/polyfill-mbstring/tree/v1.29.0" }, "funding": [ { @@ -2102,32 +2020,28 @@ "type": "tidelift" } ], - "time": "2022-11-03T14:55:06+00:00" + "time": "2024-01-29T20:11:03+00:00" }, { "name": "symfony/property-access", - "version": "v6.2.8", + "version": "v7.0.7", "source": { "type": "git", "url": "https://github.com/symfony/property-access.git", - "reference": "2ad1e0a07b8cab3e09905659d14f3b248e916374" + "reference": "8661b861480d2807eb2789ff99d034c0c71ab955" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/property-access/zipball/2ad1e0a07b8cab3e09905659d14f3b248e916374", - "reference": "2ad1e0a07b8cab3e09905659d14f3b248e916374", + "url": "https://api.github.com/repos/symfony/property-access/zipball/8661b861480d2807eb2789ff99d034c0c71ab955", + "reference": "8661b861480d2807eb2789ff99d034c0c71ab955", "shasum": "" }, "require": { - "php": ">=8.1", - "symfony/deprecation-contracts": "^2.1|^3", - "symfony/property-info": "^5.4|^6.0" + "php": ">=8.2", + "symfony/property-info": "^6.4|^7.0" }, "require-dev": { - "symfony/cache": "^5.4|^6.0" - }, - "suggest": { - "psr/cache-implementation": "To cache access methods." + "symfony/cache": "^6.4|^7.0" }, "type": "library", "autoload": { @@ -2166,7 +2080,7 @@ "reflection" ], "support": { - "source": "https://github.com/symfony/property-access/tree/v6.2.8" + "source": "https://github.com/symfony/property-access/tree/v7.0.7" }, "funding": [ { @@ -2182,44 +2096,38 @@ "type": "tidelift" } ], - "time": "2023-03-14T15:00:05+00:00" + "time": "2024-04-18T09:29:19+00:00" }, { "name": "symfony/property-info", - "version": "v6.2.8", + "version": "v7.0.7", "source": { "type": "git", "url": "https://github.com/symfony/property-info.git", - "reference": "400a019b7c05030599fd15f02b3d4ce287631732" + "reference": "f0bdb46e19ab308527b324b7ec36161f6880a532" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/property-info/zipball/400a019b7c05030599fd15f02b3d4ce287631732", - "reference": "400a019b7c05030599fd15f02b3d4ce287631732", + "url": "https://api.github.com/repos/symfony/property-info/zipball/f0bdb46e19ab308527b324b7ec36161f6880a532", + "reference": "f0bdb46e19ab308527b324b7ec36161f6880a532", "shasum": "" }, "require": { - "php": ">=8.1", - "symfony/string": "^5.4|^6.0" + "php": ">=8.2", + "symfony/string": "^6.4|^7.0" }, "conflict": { "phpdocumentor/reflection-docblock": "<5.2", "phpdocumentor/type-resolver": "<1.5.1", - "symfony/dependency-injection": "<5.4" + "symfony/dependency-injection": "<6.4", + "symfony/serializer": "<6.4" }, "require-dev": { - "doctrine/annotations": "^1.10.4|^2", "phpdocumentor/reflection-docblock": "^5.2", "phpstan/phpdoc-parser": "^1.0", - "symfony/cache": "^5.4|^6.0", - "symfony/dependency-injection": "^5.4|^6.0", - "symfony/serializer": "^5.4|^6.0" - }, - "suggest": { - "phpdocumentor/reflection-docblock": "To use the PHPDoc", - "psr/cache-implementation": "To cache results", - "symfony/doctrine-bridge": "To use Doctrine metadata", - "symfony/serializer": "To use Serializer metadata" + "symfony/cache": "^6.4|^7.0", + "symfony/dependency-injection": "^6.4|^7.0", + "symfony/serializer": "^6.4|^7.0" }, "type": "library", "autoload": { @@ -2255,7 +2163,7 @@ "validator" ], "support": { - "source": "https://github.com/symfony/property-info/tree/v6.2.8" + "source": "https://github.com/symfony/property-info/tree/v7.0.7" }, "funding": [ { @@ -2271,38 +2179,38 @@ "type": "tidelift" } ], - "time": "2023-03-14T15:00:05+00:00" + "time": "2024-04-28T11:44:19+00:00" }, { "name": "symfony/string", - "version": "v6.2.8", + "version": "v7.0.7", "source": { "type": "git", "url": "https://github.com/symfony/string.git", - "reference": "193e83bbd6617d6b2151c37fff10fa7168ebddef" + "reference": "e405b5424dc2528e02e31ba26b83a79fd4eb8f63" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/string/zipball/193e83bbd6617d6b2151c37fff10fa7168ebddef", - "reference": "193e83bbd6617d6b2151c37fff10fa7168ebddef", + "url": "https://api.github.com/repos/symfony/string/zipball/e405b5424dc2528e02e31ba26b83a79fd4eb8f63", + "reference": "e405b5424dc2528e02e31ba26b83a79fd4eb8f63", "shasum": "" }, "require": { - "php": ">=8.1", + "php": ">=8.2", "symfony/polyfill-ctype": "~1.8", "symfony/polyfill-intl-grapheme": "~1.0", "symfony/polyfill-intl-normalizer": "~1.0", "symfony/polyfill-mbstring": "~1.0" }, "conflict": { - "symfony/translation-contracts": "<2.0" + "symfony/translation-contracts": "<2.5" }, "require-dev": { - "symfony/error-handler": "^5.4|^6.0", - "symfony/http-client": "^5.4|^6.0", - "symfony/intl": "^6.2", - "symfony/translation-contracts": "^2.0|^3.0", - "symfony/var-exporter": "^5.4|^6.0" + "symfony/error-handler": "^6.4|^7.0", + "symfony/http-client": "^6.4|^7.0", + "symfony/intl": "^6.4|^7.0", + "symfony/translation-contracts": "^2.5|^3.0", + "symfony/var-exporter": "^6.4|^7.0" }, "type": "library", "autoload": { @@ -2341,7 +2249,7 @@ "utf8" ], "support": { - "source": "https://github.com/symfony/string/tree/v6.2.8" + "source": "https://github.com/symfony/string/tree/v7.0.7" }, "funding": [ { @@ -2357,26 +2265,26 @@ "type": "tidelift" } ], - "time": "2023-03-20T16:06:02+00:00" + "time": "2024-04-18T09:29:19+00:00" }, { "name": "tracy/tracy", - "version": "v2.10.2", + "version": "v2.10.7", "source": { "type": "git", "url": "https://github.com/nette/tracy.git", - "reference": "882fee7cf4258a602ad4a37461e837ed2ca1406b" + "reference": "7e7b25ba103968d5318d37db330b2e9c755dc765" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/tracy/zipball/882fee7cf4258a602ad4a37461e837ed2ca1406b", - "reference": "882fee7cf4258a602ad4a37461e837ed2ca1406b", + "url": "https://api.github.com/repos/nette/tracy/zipball/7e7b25ba103968d5318d37db330b2e9c755dc765", + "reference": "7e7b25ba103968d5318d37db330b2e9c755dc765", "shasum": "" }, "require": { "ext-json": "*", "ext-session": "*", - "php": ">=8.0 <8.3" + "php": ">=8.0 <8.4" }, "conflict": { "nette/di": "<3.0" @@ -2384,6 +2292,7 @@ "require-dev": { "latte/latte": "^2.5", "nette/di": "^3.0", + "nette/http": "^3.0", "nette/mail": "^3.0", "nette/tester": "^2.2", "nette/utils": "^3.0", @@ -2429,9 +2338,9 @@ ], "support": { "issues": "https://github.com/nette/tracy/issues", - "source": "https://github.com/nette/tracy/tree/v2.10.2" + "source": "https://github.com/nette/tracy/tree/v2.10.7" }, - "time": "2023-03-29T12:34:53+00:00" + "time": "2024-04-29T11:44:00+00:00" }, { "name": "ublaboo/datagrid", @@ -2439,21 +2348,21 @@ "source": { "type": "git", "url": "https://github.com/contributte/datagrid.git", - "reference": "d7bbdacb738565bf0adef37059b179c33104fa0f" + "reference": "86c88ed1d927aa455b5ead6e84e5e65ffbdafe9f" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/contributte/datagrid/zipball/d7bbdacb738565bf0adef37059b179c33104fa0f", - "reference": "d7bbdacb738565bf0adef37059b179c33104fa0f", + "url": "https://api.github.com/repos/contributte/datagrid/zipball/86c88ed1d927aa455b5ead6e84e5e65ffbdafe9f", + "reference": "86c88ed1d927aa455b5ead6e84e5e65ffbdafe9f", "shasum": "" }, "require": { "contributte/application": "^0.5.0", "nette/di": "^3.0.0", "nette/forms": "^3.1.3", - "nette/utils": "^3.0.1", - "php": ">=8.0", - "symfony/property-access": "^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0" + "nette/utils": "^3.0.1 || ^4.0.0", + "php": ">=8.1", + "symfony/property-access": "^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0" }, "require-dev": { "contributte/qa": "^0.3.0", @@ -2480,8 +2389,11 @@ } }, "autoload": { + "files": [ + "./compatibility.php" + ], "psr-4": { - "Ublaboo\\DataGrid\\": "src/" + "Contributte\\Datagrid\\": "src/" } }, "notification-url": "https://packagist.org/downloads/", @@ -2521,7 +2433,7 @@ "type": "github" } ], - "time": "2023-03-20T09:19:46+00:00" + "time": "2024-05-03T19:38:57+00:00" } ], "packages-dev": [ @@ -2531,21 +2443,21 @@ "source": { "type": "git", "url": "https://github.com/contributte/qa.git", - "reference": "0565ff342e32f14d6bcdaa961565287ba583fcd7" + "reference": "bf22df4d9dd2853d2036c69ef99db818a0cea17d" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/contributte/qa/zipball/0565ff342e32f14d6bcdaa961565287ba583fcd7", - "reference": "0565ff342e32f14d6bcdaa961565287ba583fcd7", + "url": "https://api.github.com/repos/contributte/qa/zipball/bf22df4d9dd2853d2036c69ef99db818a0cea17d", + "reference": "bf22df4d9dd2853d2036c69ef99db818a0cea17d", "shasum": "" }, "require": { "php": ">=8.0", - "slevomat/coding-standard": "^8.5.1", - "squizlabs/php_codesniffer": "^3.6.1" + "slevomat/coding-standard": "^8.12.1", + "squizlabs/php_codesniffer": "^3.7.2" }, "require-dev": { - "contributte/tester": "^0.1.0", + "contributte/tester": "^0.2.0", "symfony/process": "^6.0.0" }, "default-branch": true, @@ -2592,7 +2504,7 @@ "type": "github" } ], - "time": "2023-04-08T12:28:17+00:00" + "time": "2023-10-30T09:49:37+00:00" }, { "name": "contributte/tester", @@ -2758,20 +2670,20 @@ }, { "name": "nette/tester", - "version": "v2.5.0", + "version": "v2.5.2", "source": { "type": "git", "url": "https://github.com/nette/tester.git", - "reference": "78555c76859208ee049335863e63e357ba71578f" + "reference": "328d7b64579cdbc82e0e01d92ea9c58b9cf0a327" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/nette/tester/zipball/78555c76859208ee049335863e63e357ba71578f", - "reference": "78555c76859208ee049335863e63e357ba71578f", + "url": "https://api.github.com/repos/nette/tester/zipball/328d7b64579cdbc82e0e01d92ea9c58b9cf0a327", + "reference": "328d7b64579cdbc82e0e01d92ea9c58b9cf0a327", "shasum": "" }, "require": { - "php": ">=8.0 <8.3" + "php": ">=8.0 <8.4" }, "require-dev": { "ext-simplexml": "*", @@ -2827,28 +2739,30 @@ ], "support": { "issues": "https://github.com/nette/tester/issues", - "source": "https://github.com/nette/tester/tree/v2.5.0" + "source": "https://github.com/nette/tester/tree/v2.5.2" }, - "time": "2023-03-02T02:14:46+00:00" + "time": "2024-01-08T11:41:26+00:00" }, { "name": "phpstan/phpdoc-parser", - "version": "1.18.1", + "version": "1.28.0", "source": { "type": "git", "url": "https://github.com/phpstan/phpdoc-parser.git", - "reference": "22dcdfd725ddf99583bfe398fc624ad6c5004a0f" + "reference": "cd06d6b1a1b3c75b0b83f97577869fd85a3cd4fb" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpdoc-parser/zipball/22dcdfd725ddf99583bfe398fc624ad6c5004a0f", - "reference": "22dcdfd725ddf99583bfe398fc624ad6c5004a0f", + "url": "https://api.github.com/repos/phpstan/phpdoc-parser/zipball/cd06d6b1a1b3c75b0b83f97577869fd85a3cd4fb", + "reference": "cd06d6b1a1b3c75b0b83f97577869fd85a3cd4fb", "shasum": "" }, "require": { "php": "^7.2 || ^8.0" }, "require-dev": { + "doctrine/annotations": "^2.0", + "nikic/php-parser": "^4.15", "php-parallel-lint/php-parallel-lint": "^1.2", "phpstan/extension-installer": "^1.0", "phpstan/phpstan": "^1.5", @@ -2872,22 +2786,22 @@ "description": "PHPDoc parser with support for nullable, intersection and generic types", "support": { "issues": "https://github.com/phpstan/phpdoc-parser/issues", - "source": "https://github.com/phpstan/phpdoc-parser/tree/1.18.1" + "source": "https://github.com/phpstan/phpdoc-parser/tree/1.28.0" }, - "time": "2023-04-07T11:51:11+00:00" + "time": "2024-04-03T18:51:33+00:00" }, { "name": "phpstan/phpstan", - "version": "1.10.13", + "version": "1.10.67", "source": { "type": "git", "url": "https://github.com/phpstan/phpstan.git", - "reference": "f07bf8c6980b81bf9e49d44bd0caf2e737614a70" + "reference": "16ddbe776f10da6a95ebd25de7c1dbed397dc493" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpstan/zipball/f07bf8c6980b81bf9e49d44bd0caf2e737614a70", - "reference": "f07bf8c6980b81bf9e49d44bd0caf2e737614a70", + "url": "https://api.github.com/repos/phpstan/phpstan/zipball/16ddbe776f10da6a95ebd25de7c1dbed397dc493", + "reference": "16ddbe776f10da6a95ebd25de7c1dbed397dc493", "shasum": "" }, "require": { @@ -2930,31 +2844,27 @@ { "url": "https://github.com/phpstan", "type": "github" - }, - { - "url": "https://tidelift.com/funding/github/packagist/phpstan/phpstan", - "type": "tidelift" } ], - "time": "2023-04-12T19:29:52+00:00" + "time": "2024-04-16T07:22:02+00:00" }, { "name": "phpstan/phpstan-deprecation-rules", - "version": "1.1.3", + "version": "1.1.4", "source": { "type": "git", "url": "https://github.com/phpstan/phpstan-deprecation-rules.git", - "reference": "a22b36b955a2e9a3d39fe533b6c1bb5359f9c319" + "reference": "089d8a8258ed0aeefdc7b68b6c3d25572ebfdbaa" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpstan-deprecation-rules/zipball/a22b36b955a2e9a3d39fe533b6c1bb5359f9c319", - "reference": "a22b36b955a2e9a3d39fe533b6c1bb5359f9c319", + "url": "https://api.github.com/repos/phpstan/phpstan-deprecation-rules/zipball/089d8a8258ed0aeefdc7b68b6c3d25572ebfdbaa", + "reference": "089d8a8258ed0aeefdc7b68b6c3d25572ebfdbaa", "shasum": "" }, "require": { "php": "^7.2 || ^8.0", - "phpstan/phpstan": "^1.10" + "phpstan/phpstan": "^1.10.3" }, "require-dev": { "php-parallel-lint/php-parallel-lint": "^1.2", @@ -2982,9 +2892,9 @@ "description": "PHPStan rules for detecting usage of deprecated classes, methods, properties, constants and traits.", "support": { "issues": "https://github.com/phpstan/phpstan-deprecation-rules/issues", - "source": "https://github.com/phpstan/phpstan-deprecation-rules/tree/1.1.3" + "source": "https://github.com/phpstan/phpstan-deprecation-rules/tree/1.1.4" }, - "time": "2023-03-17T07:50:08+00:00" + "time": "2023-08-05T09:02:04+00:00" }, { "name": "phpstan/phpstan-dibi", @@ -3105,21 +3015,21 @@ }, { "name": "phpstan/phpstan-strict-rules", - "version": "1.5.1", + "version": "1.5.5", "source": { "type": "git", "url": "https://github.com/phpstan/phpstan-strict-rules.git", - "reference": "b21c03d4f6f3a446e4311155f4be9d65048218e6" + "reference": "2e193a07651a6f4be3baa44ddb21d822681f5918" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpstan-strict-rules/zipball/b21c03d4f6f3a446e4311155f4be9d65048218e6", - "reference": "b21c03d4f6f3a446e4311155f4be9d65048218e6", + "url": "https://api.github.com/repos/phpstan/phpstan-strict-rules/zipball/2e193a07651a6f4be3baa44ddb21d822681f5918", + "reference": "2e193a07651a6f4be3baa44ddb21d822681f5918", "shasum": "" }, "require": { "php": "^7.2 || ^8.0", - "phpstan/phpstan": "^1.10" + "phpstan/phpstan": "^1.10.60" }, "require-dev": { "nikic/php-parser": "^4.13.0", @@ -3148,38 +3058,38 @@ "description": "Extra strict and opinionated rules for PHPStan", "support": { "issues": "https://github.com/phpstan/phpstan-strict-rules/issues", - "source": "https://github.com/phpstan/phpstan-strict-rules/tree/1.5.1" + "source": "https://github.com/phpstan/phpstan-strict-rules/tree/1.5.5" }, - "time": "2023-03-29T14:47:40+00:00" + "time": "2024-04-19T15:12:26+00:00" }, { "name": "slevomat/coding-standard", - "version": "8.10.0", + "version": "8.15.0", "source": { "type": "git", "url": "https://github.com/slevomat/coding-standard.git", - "reference": "c4e213e6e57f741451a08e68ef838802eec92287" + "reference": "7d1d957421618a3803b593ec31ace470177d7817" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/slevomat/coding-standard/zipball/c4e213e6e57f741451a08e68ef838802eec92287", - "reference": "c4e213e6e57f741451a08e68ef838802eec92287", + "url": "https://api.github.com/repos/slevomat/coding-standard/zipball/7d1d957421618a3803b593ec31ace470177d7817", + "reference": "7d1d957421618a3803b593ec31ace470177d7817", "shasum": "" }, "require": { "dealerdirect/phpcodesniffer-composer-installer": "^0.6.2 || ^0.7 || ^1.0", "php": "^7.2 || ^8.0", - "phpstan/phpdoc-parser": ">=1.18.0 <1.19.0", - "squizlabs/php_codesniffer": "^3.7.1" + "phpstan/phpdoc-parser": "^1.23.1", + "squizlabs/php_codesniffer": "^3.9.0" }, "require-dev": { "phing/phing": "2.17.4", "php-parallel-lint/php-parallel-lint": "1.3.2", - "phpstan/phpstan": "1.4.10|1.10.11", - "phpstan/phpstan-deprecation-rules": "1.1.3", - "phpstan/phpstan-phpunit": "1.0.0|1.3.11", - "phpstan/phpstan-strict-rules": "1.5.1", - "phpunit/phpunit": "7.5.20|8.5.21|9.6.6|10.0.19" + "phpstan/phpstan": "1.10.60", + "phpstan/phpstan-deprecation-rules": "1.1.4", + "phpstan/phpstan-phpunit": "1.3.16", + "phpstan/phpstan-strict-rules": "1.5.2", + "phpunit/phpunit": "8.5.21|9.6.8|10.5.11" }, "type": "phpcodesniffer-standard", "extra": { @@ -3203,7 +3113,7 @@ ], "support": { "issues": "https://github.com/slevomat/coding-standard/issues", - "source": "https://github.com/slevomat/coding-standard/tree/8.10.0" + "source": "https://github.com/slevomat/coding-standard/tree/8.15.0" }, "funding": [ { @@ -3215,20 +3125,20 @@ "type": "tidelift" } ], - "time": "2023-04-10T07:39:29+00:00" + "time": "2024-03-09T15:20:58+00:00" }, { "name": "squizlabs/php_codesniffer", - "version": "3.7.2", + "version": "3.9.2", "source": { "type": "git", - "url": "https://github.com/squizlabs/PHP_CodeSniffer.git", - "reference": "ed8e00df0a83aa96acf703f8c2979ff33341f879" + "url": "https://github.com/PHPCSStandards/PHP_CodeSniffer.git", + "reference": "aac1f6f347a5c5ac6bc98ad395007df00990f480" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/squizlabs/PHP_CodeSniffer/zipball/ed8e00df0a83aa96acf703f8c2979ff33341f879", - "reference": "ed8e00df0a83aa96acf703f8c2979ff33341f879", + "url": "https://api.github.com/repos/PHPCSStandards/PHP_CodeSniffer/zipball/aac1f6f347a5c5ac6bc98ad395007df00990f480", + "reference": "aac1f6f347a5c5ac6bc98ad395007df00990f480", "shasum": "" }, "require": { @@ -3238,11 +3148,11 @@ "php": ">=5.4.0" }, "require-dev": { - "phpunit/phpunit": "^4.0 || ^5.0 || ^6.0 || ^7.0" + "phpunit/phpunit": "^4.0 || ^5.0 || ^6.0 || ^7.0 || ^8.0 || ^9.3.4" }, "bin": [ - "bin/phpcs", - "bin/phpcbf" + "bin/phpcbf", + "bin/phpcs" ], "type": "library", "extra": { @@ -3257,22 +3167,45 @@ "authors": [ { "name": "Greg Sherwood", - "role": "lead" + "role": "Former lead" + }, + { + "name": "Juliette Reinders Folmer", + "role": "Current lead" + }, + { + "name": "Contributors", + "homepage": "https://github.com/PHPCSStandards/PHP_CodeSniffer/graphs/contributors" } ], "description": "PHP_CodeSniffer tokenizes PHP, JavaScript and CSS files and detects violations of a defined set of coding standards.", - "homepage": "https://github.com/squizlabs/PHP_CodeSniffer", + "homepage": "https://github.com/PHPCSStandards/PHP_CodeSniffer", "keywords": [ "phpcs", "standards", "static analysis" ], "support": { - "issues": "https://github.com/squizlabs/PHP_CodeSniffer/issues", - "source": "https://github.com/squizlabs/PHP_CodeSniffer", - "wiki": "https://github.com/squizlabs/PHP_CodeSniffer/wiki" + "issues": "https://github.com/PHPCSStandards/PHP_CodeSniffer/issues", + "security": "https://github.com/PHPCSStandards/PHP_CodeSniffer/security/policy", + "source": "https://github.com/PHPCSStandards/PHP_CodeSniffer", + "wiki": "https://github.com/PHPCSStandards/PHP_CodeSniffer/wiki" }, - "time": "2023-02-22T23:07:41+00:00" + "funding": [ + { + "url": "https://github.com/PHPCSStandards", + "type": "github" + }, + { + "url": "https://github.com/jrfnl", + "type": "github" + }, + { + "url": "https://opencollective.com/php_codesniffer", + "type": "open_collective" + } + ], + "time": "2024-04-23T20:25:34+00:00" } ], "aliases": [], @@ -3286,5 +3219,5 @@ "php": ">= 8.1" }, "platform-dev": [], - "plugin-api-version": "2.3.0" + "plugin-api-version": "2.6.0" }