From 2e6cf8734b74cbca813a1bc772be2850d715e7db Mon Sep 17 00:00:00 2001 From: Will Hunt <2072976+Half-Shot@users.noreply.github.com> Date: Mon, 12 Jan 2026 21:13:15 +0000 Subject: [PATCH] Refactor RoomStatusBar into MVVM (#31523) * Refactor RoomStatusBar into MVVM * cleanup * updated snaps * More cleanup * fix loop * fixup * drop comment * lint * cleanup console statements * Starting to move to a MVVM v2 component. * extra * Refactor as a shared-componend / MVVM v2 * some cleanup * i18n for banner * remove removed css * Update playwright tests to have a two stage on the consent bar. * Update snaps * Update snapshots * cleanup * update snaps * refactor to use enum * fix slight differences in pw snaps * Add unit tests * fix snaps * snaps updated * more test cleanups * fix snaps * fixed now? * Disable animationsq * lint lint lint * remove console * lint * fix snap * Refactor based on review comments. * update view model test * oops! * fix snap * Update snaps * snap snap snap * switch to a const map of strings * Use this.disposables * Update translations to be inside shared-components * fix the tac * Also retry * Cleanup * update snaps * update other snaps * snap updates --- .../.storybook/test-runner.ts | 2 +- ...tusbarview--with-connection-lost-linux.png | Bin 0 -> 17602 bytes ...statusbarview--with-consent-link-linux.png | Bin 0 -> 19867 bytes ...usbarview--with-local-room-retry-linux.png | Bin 0 -> 13808 bytes ...atusbarview--with-resource-limit-linux.png | Bin 0 -> 26443 bytes ...tusbarview--with-unsent-messages-linux.png | Bin 0 -> 23343 bytes ...ew--with-unsent-messages-sending-linux.png | Bin 0 -> 18665 bytes .../src/composer/Banner/Banner.tsx | 17 +- .../src/i18n/strings/en_EN.json | 18 +- packages/shared-components/src/index.ts | 1 + .../RoomStatusBarView.module.css | 11 + .../RoomStatusBarView.stories.tsx | 105 ++++ .../RoomStatusBar/RoomStatusBarView.test.tsx | 69 +++ .../room/RoomStatusBar/RoomStatusBarView.tsx | 310 +++++++++++ .../RoomStatusBarView.test.tsx.snap | 520 ++++++++++++++++++ .../src/room/RoomStatusBar/index.ts | 8 + playwright/e2e/room/room-status-bar.spec.ts | 9 +- .../connectivity-lost-linux.png | Bin 8786 -> 12452 bytes .../room-status-bar.spec.ts/consent-linux.png | Bin 15218 -> 14338 bytes .../local-room-create-failed-linux.png | Bin 5965 -> 8394 bytes .../message-failed-linux.png | Bin 11561 -> 16999 bytes res/css/_components.pcss | 1 - res/css/structures/_RoomStatusBar.pcss | 175 ------ src/RoomNotifs.ts | 26 +- src/components/structures/RoomStatusBar.tsx | 297 ---------- .../RoomStatusBarUnsentMessages.tsx | 36 -- src/components/structures/RoomView.tsx | 70 ++- src/components/structures/TimelinePanel.tsx | 2 + src/i18n/strings/en_EN.json | 12 - .../notifications/RoomNotificationState.ts | 1 - src/viewmodels/room/RoomStatusBar.ts | 223 ++++++++ test/test-utils/test-utils.ts | 8 +- test/unit-tests/RoomNotifs-test.ts | 63 +++ .../structures/RoomStatusBar-test.tsx | 150 ----- .../RoomStatusBarUnsentMessages-test.tsx | 39 -- .../__snapshots__/RoomStatusBar-test.tsx.snap | 182 ------ .../__snapshots__/RoomView-test.tsx.snap | 152 ++--- .../RoomNotificationState-test.ts | 11 +- test/viewmodels/room/RoomStatusBar-test.ts | 166 ++++++ 39 files changed, 1662 insertions(+), 1022 deletions(-) create mode 100644 packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-connection-lost-linux.png create mode 100644 packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-consent-link-linux.png create mode 100644 packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-local-room-retry-linux.png create mode 100644 packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-resource-limit-linux.png create mode 100644 packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-unsent-messages-linux.png create mode 100644 packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-unsent-messages-sending-linux.png create mode 100644 packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.module.css create mode 100644 packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.stories.tsx create mode 100644 packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.test.tsx create mode 100644 packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.tsx create mode 100644 packages/shared-components/src/room/RoomStatusBar/__snapshots__/RoomStatusBarView.test.tsx.snap create mode 100644 packages/shared-components/src/room/RoomStatusBar/index.ts delete mode 100644 res/css/structures/_RoomStatusBar.pcss delete mode 100644 src/components/structures/RoomStatusBar.tsx delete mode 100644 src/components/structures/RoomStatusBarUnsentMessages.tsx create mode 100644 src/viewmodels/room/RoomStatusBar.ts delete mode 100644 test/unit-tests/components/structures/RoomStatusBar-test.tsx delete mode 100644 test/unit-tests/components/structures/RoomStatusBarUnsentMessages-test.tsx delete mode 100644 test/unit-tests/components/structures/__snapshots__/RoomStatusBar-test.tsx.snap create mode 100644 test/viewmodels/room/RoomStatusBar-test.ts diff --git a/packages/shared-components/.storybook/test-runner.ts b/packages/shared-components/.storybook/test-runner.ts index 5f0748115a..92f886a1da 100644 --- a/packages/shared-components/.storybook/test-runner.ts +++ b/packages/shared-components/.storybook/test-runner.ts @@ -20,7 +20,7 @@ const config: TestRunnerConfig = { // If you want to take screenshot of multiple browsers, use // page.context().browser().browserType().name() to get the browser name to prefix the file name - const image = await page.screenshot(); + const image = await page.screenshot({ animations: "disabled" }); expect(image).toMatchImageSnapshot({ customSnapshotsDir, customSnapshotIdentifier: `${context.id}-${process.platform}`, diff --git a/packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-connection-lost-linux.png b/packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-connection-lost-linux.png new file mode 100644 index 0000000000000000000000000000000000000000..59e59e4461086f8f2453650c50cc4f3c4880fe82 GIT binary patch literal 17602 zcmeHvd010dx3|_RZB=M%6%iqAQBe_45fC9sy^2&35RoxJstAY}B48L2l31-GAW%U- zrbMC4Lqz5wL}d~PL43i#=a#*sx*y`5(_--mqcwdiRs}pMA34`~bMHal?i$H=I9v`bt#J^2F8{ z8e#&h;yuu{Znp^44IP;|di`M554SanH(vPU@Vvu|ol#{aL0+EvO~Wc3&-0|qy{kh` z4#ve_+Sx#x<%)gM@>66#o#EhM3i7u1Vp#u zId6hl!3Ho!9qg-hDwcVJ->)~H-QBQloun^6{b~K+-nSbztyA{t#@!n>-2L{m*XyS~ zJ-uPeh7I3-_Q}!pgVSH$U8nrBd;hZ`hcqTL7=S(NBVHGAUb?EY2bWwlU&l_MT)u%N zT&p@;Qbgx96LsE0q)1{Kfxg}-TbV`Q*1;h0x@1=b<8mHcK;(7=X!{W5H+$4g?WwfO~JF(QFgQ5*FuQzr_dRgi@ z5?GNav*-1zBBT+Nu-?efL?_!t_|Lv8<4KhLu77=$H8&}kLmi_-n^qFkJAR)8_nrF3 zh1n9)<|f+&j?bC-kQ+-_jf~J~Ic=>KHP@L4k^Wr_J6)d2c1*sK{y{5J=(sQon5zGw z{sx)#*Q`oqhiF%(Z}m9c)m9rxUpIcJ3ZHh)4>0IVgCkq(K^j{m-Syrzl zC>6<$61)h1b^w=IRr@a3E^dtKc-3iO>!7Gk^@c~ffpG?;f~e_n)OZQ|q_ z^M{b}HIPNfmd77C9&7fm4$pG>&;{k^E2TTF`+u^On}x*S_gHS~Y}@*L*An-XZYJrCz;6!(S@xAM%K~2^|dN`16V}x&+d^&A6 zPOPyQs6Q1olgVnC93LQVJ-$xTV>jTr9K;)Ju6ff5L#tLy=Vn8!e>*;77_%}R;>phd zNE+(|nqjakmZppy?- z!B=ynE~a3(@T%Q*z#5U|1ks0|lyhzpFCJ!69TODGGl8Oai6ZRe# zx9+SJ(Jw=e!Iq!5gDB1Dfp}Ca__tz8sGqv(R{z=n(NrE7Cdh6bM$FHuB}oGNuic+S z)il>)^y`ig7s}fa+re^veb(IdzG*O5UAq)OI}4ffrmN>&OtCKx#1rs>`p|qke9B1O zha5PPTQQc)4)2?Gw_w~9&Th3ZuS{Qy*MPUIu3bHI;arZW?T{%UC`y^WlN!==r~T0f zTQtf0_%-s#65hKBk%6k=&XT;bv-5DA_uxtv-XW(789ZIpb3nb)a*UXCf!wz8GdsCi z`9LHhU{{x~c73zGNmzIYyW4uI!Bi>XrBn|{AeP3=u_&Kv49zH1<%a>24phaWmL#{y z^5qvS3eJ}rQ+r~}%hjS$g~MIKI@Qzgu$ToQ#PlTg;wnxPD~SEn6?7;A?qQ%-Th)SfAA{e5UzcsLW~0wLONhaCv<~{2;I5vswB$n zh`fAd00nrK`>)Z>lQP0=}fiP8r{XVkf6~D$MFu z2nx%|+1~Aq-NTc4*FFcW7@bJ=nntA$F5&0B6A{3{Rbx1 zx5gDK(_mkHL^^svpuwGxiYvC8x$N` zSB)SD&hAupw{Az0rdlN#kj_;H+C zVSH1YC2d>Rgr<{$^AeNhJg45x$rH%_ovFPyz0Q`YtT2l9Zc|$&Mb76;w+@5zmy<#> z9%naxAeL2O@&cG5Iq68yXf5Nk^K5(xU3o|G`0N4J(di~xT#tHir#q%7G*9*Nd8uu} z>H<9n$bFNU#yRI3HoEh^rk8l6J-pMwB!Q&P8lUw_F&ATuV(Qso_FX1ak6Gp#hR};p z9MVocX=51-mfrl*?e817+zFpG#QG%HX0T3Xz!4y(Wg^`j?pNMdG#t%WSzk|_j)r}) zBwu@#DY-~^oab0{v4KO9Yu_qEqX!qDq^teQs6tb~@w(7bYn-4=mvX4jTd+*A!$_W_ zC1@W(vwvf*OXkEK$Dm$wiYkwP#{7&$Kk_L5S$TTSUvJ8AV@BdBG;Nbh#+7fj??LfL2FZx(I@SYn9_Wm$ z-s`BKplA-h+ck%Dv!DDb(Yg1ufn3}FoIsZ~mE{>Tbf}2Z0&bK}s+*#gzsnqu4cynt zQe7GyvfXLWTmzB5buon}UPwCi0-LQDp5hs%usVZ(W>bC5Z{gRi6o9KYaOqxb`hnK- zN9TJOA%KZvRk1oG8@3STev!y)+$z^+1vo)$%eW=rSmRtu0B?IwDLIA^vV&B zSFLq|vbYReW0bdI8elkAA)Z&H6)D5!mJNMD>I7wY7T0kit0(Jh`{Jp!Uk2Lj&0?|9 z@8{! zx}HW>8qo=H0e{^mt#E!7wY#5c7(i?ETn`&+NICFw^wBFPu-xMMPAd}cDKW$vAE;tr8oxvwhzX7YuLL#6@!(W|pP_X@PYq~kZOgmSQY z_+8yVdYf4~{usBwFwg|dLDQ~>(oE z_K4rLZo4}uQ3J0rPtsag7<1nLc#cpf%H!&Blk2<|PFgqS9d)%GQU}Y>yr~mfo{cdP^YebK2{2Z6ul9bvl^Jy6YsB6Y%a2+lOll$i ztHhgh!a=9so~KVd6rW$V;%B+}kluqN%=p?erdPB1&D4QgpzOK}Dr{RQM7(>v?4Vin zcuIdoo;JFq?LR~qyLc$*9A@xt(TJoGJIUM%iebYG?qA;|OiWN(qC zb?7C$*x3;w4KZ9v6hZbRGppREqeFrP4^n0IDCDAjT&%)yu9bgw${BkOzaut+*(B`O zYWgT-(?I3aO9Mfwqy|j|!k*AozoyK`EvavRSTm}#;8xDkj3JQgbv(;*VbW$(V3^EZ zzxzhyyXSsRdx2~A5A?o>sQ(1A3;RO#BKk=6%Nn0^SE@oM77;u7oE_#j#*@r^d|R)! z4Z3!3a!@Z6=ix093BFk#saAco>*b?aw_4=Q%n}LYLnd^*O={;nq+q9m>j+z9$@P|- z{&WYG*B=zkwE;IWRqm4k=NIxN=1#zR+2Yc4nNb!1);r}Nr!FmYwCBCAR5tX2ET8jy zZ9+n>o}SuB>+EswHL4d=`bI#l1u;xTEk}zt@gm5g9t>gecL_$spnR1SHI=MmO>z3K z-Wj*<YScUV3kXnV2A&xvcnbttW=PgR}ra>wM<)G3@(#Zlue6J30Z)G2Htt4AU{o@3Z)E5 zgY)li+0LUD@~>xcuTbY8y6R`{r-U<1onZklQ;{qkHb!ZITla-$NP|WKf}chm%<>#* zJjo}+mvjZJs3Mg)?nJIOk@oSBSn2M#ek!yW;RnpfXye4StZQ1JZUi4%rJcEq*l*2qdzgL zqeKftp6{)nMD0kvROFC(6oq(7Ma?+t9rv?hz)yE-jI{NeRZ}@kjKS1Wud3Fj>Hty; zfLI+sBN6XLQesXqj(!fI57o?vuFgg(f~NeaxE!hA=Ld1AnZz3$nq(Pl6>P7rjq!U$ zFoL$6;u}AFE9QJL7J0+M86A1?O2}2ZW}Hn+twlYW(7uM<>-5Eai99e)}7$=)(Gnwn@nW~3a0 za4#w(r!`yWBC!{T?g>=Eyqq&1?j~SQ+*D~5w%BkMU#OepFBOlChs%61`3FKDwVlJt zg$7&Wt+A+?`xy?Hg*t%hhUmF?;8kD|d2~o;;XZDI(ub;)b?{SO$vlKkY&-wcuNuVZ|fHtXRHvVx=&J6FejE?V8Hw6eszS2(O z0F`usp<328Fdouqo=^ySwk=f~TZGMCcOB(!k;!U=Xx=6HCPuR_;9LGr;)MKUm?dI$ z(Het6WLImPqcDM(vDLQD@uMH!Yg+eTU7GqFyhdw?Hr7BdO;sm{0Ekv*nLT3wCdvNv z`8VgS54^lHJOf!YT)Az(+3qscQOSJkKu3@*cW*d7l%f44=8TD zex54V23ZHcF?NT3l{-L^@t4#m0y*0K&tk%ZxG4J7TkLSA$m=*Nr=@FW>)a?lQPCel z0UH=JZlgP?CkSCq%0(+X*Ccs=a*=yP^R-pH$&tR1W~h!35cqG;;4WsG2cTF!FTmCgY7;#LcjTq$_}|%s9_vuAMYL9J1VUHZADp;6DDe|w76@5?x^f2K5f-o168wK@2qGRm{eRfg^?6;i$x1H8Jr)2=oMqp4Hi zhYjWIyf0uY78a=_glYjSl`C?X+TJ4K>CMgo8E{{0oA~pV7no1f$d8UU(~OcR@8(3T z4(Kh#uFBW%?u8he>V0Xz<@xN1vD|=$m+H~LZ7@IuT3omldq*s>Hkw7w(TX-4vdM z%#iLKdS?oy^WeT(F0o8hP9??3`r5nIz;8o$cC=wneb6=(nRr5@3D3lap63ci4c3p<*@>cV%LN}l zQU^O!IG3oq$1L)GG7Vl<;e(vAoGN3EiB9@(mDIYXwIwJRPS+~XuI0&ApnjRgk{+v1 z>2RMIs;6J4x@=+u!c`0(+x(&b47v2*!F>>uU6*v3{{pwca&CDf2~(uVeY@7#6|iif zJaAnfbHj~d5FvlD*5j%R!1JAxbm!O7EejnQ_^Z7pL>1JT>l}y^6ufnsZ@`a+8nv$j z;{m_pzaKGR-qLi*+LxqH%WVA;&6mK-Q6lmv3iMv=&UF+$4g~jvZqg$}BNjQ44r}bi zVgY~J6fkOTFckfn_(G!YIy{`1y>a?#(t0K5N5zB47Kv8P{9-@}%Uj%oOJ2pW-Q=rN zM1(dIL73{uteO4_U9V;#9ER~^ZBnLYHSiWuU@Mj{36EKzT}-Pd`87cG6iaiE#U z6`zSUjs{8Zg+RwRc90m8X8Apxk3oSqH`B5QdtDsK=dID;1%u&TIy$IR@6rnhu;|(0 z`Dw7mU!e#Dw4&t4bzs|icz`Kb49%Z1aywTNJSv^6OrFqPhseJyr_BB)TqUl4da^F| zh>F)$t!b19dP;87QXcFw4~dCfk0nGs`)}2n>Lf0H-G;zRgGOGe@V@b&Yf#bae7G-i zI3$@m`!g7x&;yYHyAt!r@O4$LS!6;0x@Wqv zEy?=%Er?`aF9KC=InC(L|p-UB&iUCmZ8?$m~aJTS5@OuutX+p4s8aV$m^t`T#~PWsO1!XKidd}nSfb??>UQn8<4zX|#jJ1XB%f zmw!pS`}@)@1~wLcZ+yXZYB!?}y|;Gwd44m9|AWZStTfQZMNUeXHgeyel?Rw!C9Y@irffdCU@KNl-9p~^7*L{&~ zxZn(@hFMjQW^TS^Z!f(ybz(N5t;rB~o8(*dT{=t95N@aM{A(SI8n1oeB3dR|^mr<6 z)bCQWgY4#ty6Rdi`6eIz}P<6NLe2-e>=i@pPf`{H%Cx5ivdZfPpr zoNRLk>*;SZmOk9d3(9Z3lBHWV)(6sM@8c`PV{yT;IqJmLih5UK6pLb*Cb3~#`!!#0 zr-QI<9D*41K|rxtb(_l1tshpOd-E{!aYQC#ZH|u1JON`G?L<_Z0$AN%?nWn=)pwL- zfRD`%6uH6T@-~f$*Lt3PC=dx+&}CyijmbdVvu+3erdL`wEhmk-MCE94T?wJQ91`8; z15XBWo+;|*E+Xfp^s*gYeTP9|lOYgn+}FHd`P!~b>Xs~ zRkgn>wA3ew32;pt6!~uXtd>J`Oo+0Utv?<-^sc>;XeO_;E~?d6rasa8Iyk^*>X8`) zk77Efxo|Nj7N6CZmggzEGm?QP;9Xu7Io2Z8Apx`eVlQtXe5J$ySre>NhMXpbr_|3a z1oM1pbtm$#+0J$*^2byBI+JAALd!Ac5zBikynH;BjxC6VVuB_Q67@sP*(}nxe_{dI zwNLb63~$xA&>DaW@`t%OFFeV2Jb7)}&%sCm)(An)Kh)N2oNvjG_ltw^NTl+^RWRgI zf7f=vsh2LYrqO0HV=^hakACi(1b5P@Sz2r$NgRQ^O5fP#v=?!9NeCNGz-NMH7u=z& zl@LsGN~_`H-OjSc8*Nju`kB>Hob;%%jnS~A-4-^DA(3Q3X&`|pAD&8y)HWH57?%ca z?>>aR)+1aO49A!^HyG0m#|-yo5o0=GF4~6LlnFSt0xKd)Ts5uWz!&n4vFILXD<@U$d)cYr76O z#Z*jWvh+|{PN zqo&MDh4f$Q&xOD+0rYWQ&hh$MxN!;BY7S*MTM0eN#~B)ujhkw)vgPxs_?|tO?gHTI z&0S6n$`{RJ-*^w1g3)p}SNp(=(Z)|UkeK_e2f)A}=Btpl)oHZ!IRe4s7_b(-LTj5#CC;`+6sE)Xar`50KW$~4lW8mOj(s2-5z zBFax*H`X$#YKD)-{J@grz-pQWPRTGY7aT}YUUmWOUc2@N>VRx2XIpOB1~?hnA?RS) z_+2S74u_7n4)-$(0UpPnPm^QkT76wp-c@EB`FhtiuGj;^N&_a8@AE7SOh|eA2;x3F zxKj?~&8!~?KOT{>{B#$r(u3cB*M-vjJotMZi$p{2v@+FgCtf^3h)hU#Xp#@a!M-p# zd5hETGdDAyR8@>b*e+2`_Y8lBJ~Ild2dUS|7+XFKYJH>_9QK6Hjegt+IyWJT0CJixsP$JJgLY zx`Nog?=g&EGj8+JlOj~a-o1GK+FK#Pd-eWcOM4X#dB<%O;v++Yh*BShf)*TP=zC}O zs}7CwToGH2>)DI!_P3jXDOjIJDyA#n-b>iB*M$_d1$yUPvT!GrWleEz3%ubP#*g8} z62GuC^{DfoDD5-o2iL=w)`F9nXu;!*El0eiwWaqjmKD zzY1g=P&wiwZS7NY2#%C8_~{Qe zwIVMZFPV!_i_EN*3;G5{e3;WdHG<)!73=YPIkl?!H#vg}oBa1gCm|T)h=llYH2>Y`i9VBE{SaDA(?AZ}HqoIRAJi zV)^N#Z>@c$AfAGJcplu~9+d6IX_B0(w4dwT>FTPR-tU`Bjl3;scVP+dH)$@gn!-K| zA`pFb7bq8?Bw?I(dIfXuECM*kFa-F%59@L+^))hbS~~R-wbWiy7oa(`$H;O& z37tAz7f5LX<6GrM6D#Y0R($cyqY#Y(TjOv|9-VkFm@ctjRvrG@$s84ND{a1-apz`s z&Ihd;*K4+-`O!m2PRIVGRNh|ShP=84IJ+gQAe=rYodY#f8YDV(63zjomZRC-;X<8S<&d;M0tkn+kz zI-zr_P3wI5>vo%O>boBs;x_SuI(=gdFt^nkC$_GxCTJvCu~(h#zWI$4gR`c&;-{9| ze=Hls5XWe4PvKFLO=Ji%qsS=(z*A@e+*wMsb-yv|qlj!m*6HZJ|-wUDbpLCz5{ z*QqDL*Q~A>XG^Y+LR|S|6R3((Ei(kWM4XBhZqnj~-w1X428$Y9cCCUyUfBBJF>Ij58nfmVs5+c z#9)#=siyOK%OEa1~_v;&u}C!1F8Nq*SXV z{Q6@oKdz@{lRZjPN03%|rr*X4+i&LN*o3%@_}*D!4ZBVzi>11b(Dm3MIy*)<%L;(R{RLYYcKWS0d`dD?boIx)K*qG|2Z znQ`a)`+F|xmxe^Td-*Wx>P&!!)qL+)n&TjFGepZ8I*_ERRJk`Lw4~rB@-zZWed!fS zqXY}>#QCtFVmORANGg48X_T76u5OHQu^FRgp1|D}@Y~Vj-lUwxuIg~Di{7`RsX0Tu zx=_c(uVG#hf?-ekOKOdWw zy6?XWFVZXUpQB@02U?>g_DjSFiB6Wc4TBxsr8to@lAhd>Cr;y|Rl)0CE8yn(ele}^ zkJVKLOZskO6a!?V4^?-*-RaEM&)sv+Cn6S?f6nblV{=}Mg)z9ul>ve_D{3nHRIVjW z2%aFg)WsTKQ%6xbM9K{owPi%}iA3CvUOAW~uuAC`gCmSD{M=T#ACOOOr zK96+DUb$GbwVB);e6BAv&>I;PTXSRD$ddI;k&Q(Ll$F=SJ9K}U(oj?zw*jwE3*Dlv zG{k$O=Qabi#-&Gj6YQOaH82?i>nnGZ4%=&|4Z}_qJ27aReO}=pHBmwSK8&jmG6x=N zMGz4V8wnxQxwAjrNE=>!Jx)V}Ot3sWPQAW6B*ecva+ zHza!^c4jYqO*qfm1@nSBJ4gP+4Po!AI3T+#KI)ecHkjpjfd8~12JOWt_vtr;6$#GA zNcQ7sr7#+fyDTq5!#atnZhJ9r()@Pdw`QjU6=mnQXS^@9r+mlaTJ38Moh?VHKtYRn zA?y?CEo9BOr>)HeuFVY#o3}$}_fU#LTv|+2r~3tWwd(UC_@e+;2I--$rRu|9V9A%A z>Rd_>{Abmj#kqJ-7hdj~P}g-kucN}pT|7Qmnv*w`E zi;)>RH77y-`5X%X)nLgonx!JwRsnt6Eo~kD;+i;>RX!YN97-u^4gE&R_9g1GVZn9 zZxX`<;^m?Yn))GUtiuU>^s29IOqUyC*2!r%IMjJH-x#88=!;K}dY7IabxPZb4D&fc zm|2->DyZH?(o62JAU4jI%+wo?1z3V*A%qjS(YmFd`Thy%w~7Vbi_ihu!sWrzsRy=kf@F8o+%UOMY7es?gSQ$L zZOiwmydg28m9DKgE*R}fuW;xed3$I_27~37cC1}|)UZ!p{?zRXEP6E0 z7Ea?bpjv-8W0HZa_~aGHbBPi}ET%O2KSV)r@`#Cc##8Ez~+4_6W>$I z<2wo+a&9lB#vLlH=;ehEzAQhe&j4-e-eXS7shjX3q1DDDBk%`uLK3WADG}aM&+E&C zwAf@NlJkp(p|^~~21pQp2DqaThG`Bvwb-X2YsWmUOv=XR26H;Tx)Je+$s$o7W@K=mR6kG+Z@71?<%y!<7@7j=;fj2u8Vmi zhtUu(%=yzXolSLJyZm`~j2)IFds>8pYsgzvLUaxH{PDprTt% z@G%4_`g>sM#M9xR_8<)ldG5J|4z$L04*|KonGL&;GdxGe8IatvGFnT1gUP5`-iZA_ z6RZEk0+hOJ3>)0_xFYio%f}sf8Itxa69d(y0u7)1kX6x5p70Lp6$;z7h;q$7)CE`O z4#{4d0GlJaJsYWeM$$dU>zx=3fNEiwa)&!o8+hK?SA?oGsmrHSkOt}xga}LQY(<38 zg?{d{pO-a(DE$*~uND{9{Z#OF-2!b*h3vd84>jdZw`mD#V+_2p!&?`-L>zG&FH*e+ z2S?1q`sTvdMLQk0R_m+xdj(T=nscq@!e*z5qK z>Rl8!=T>Sqb=1DR;r5p%^Bh+8eAEt#UY!;e8vlP?Bw};_75(3|a7Es1xdTYbC zCN$|Wi4Zxt2ZqW@4ItTlSFqEyIfUz{Wy*~X2y%9lf%wC4taMK$y@>Y5{!Ly6I{q4? zu3&8?YAO9X3}d4VtR(oZNEkdP>)BNTqF;43xmimL=)%>9JOlD8Jz=d8192Ur0Um(< zze5LLX{-Oar}0{%UGoRWLa!(Te@iChBG`aVCx_Oqlj}E-x2{39`!xc19ZDWS$z%!U zhW*WoDo)-0fmJs;&{c&cs;V3R&T4QXs9$UDwhZxpni9#HSO`C_d_1&k6b4$4#C>ql z0*T3wrAF1Hlfq!M_4T66OsBdK6TFbYQV03^NS+ub+w9}reI0n_51n@fbCIt%Iv)lt zL!SFttG!QC9Up(p6!>pI{_nWH5~WCu+A6HHOYB(xhT&g#ufIWmCB|mw`lE6ZJaIh) zGU<}RJYJB29f984X=_~oBVwS-V0mEi$6Sy)3)b@JPSliBN8 zA~R2}bsyM8T@N2Ix6QXL_uU1N|JA{$xh}%*a2wR5&({AEgfPC0DwKbP+2Zl9m054V z6ImZ4IlL(J>Kj4-a04G5{I9$Nt-ybESb#3S5+GIi**Y7auV>jX{(bVlb3v<=pk`@g z$RN*k#em?oZol=V;QkvOzY`>pgFd=B>-j);(U-hF@?hitDk13qA&2OnA^+Q~tA9B5 z56Aw|%Kv$m;y?QGkG}k)FaPMv|1hcfA9L}aG#6(#Z20Ae|K|kr|4-K9pj%MjdLq8v z$M*&N2h;QaKjGd#9Q#kb&*2||`A?d@b#(7P^q!6X&ANP0Yi!t{R#*RY%wXMp-|~k^ aDZGP1Tm`+WT|cwoyshKe%K!T5-v0qZ6pUv8 literal 0 HcmV?d00001 diff --git a/packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-consent-link-linux.png b/packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-consent-link-linux.png new file mode 100644 index 0000000000000000000000000000000000000000..f4be9ccdc19f10b7029944a42842caafd6f3c821 GIT binary patch literal 19867 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 S!}2={SFP( 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 literal 0 HcmV?d00001 diff --git a/packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-resource-limit-linux.png b/packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-resource-limit-linux.png new file mode 100644 index 0000000000000000000000000000000000000000..7ccad17abb0ee35d7d89428df1b58caafdd874e4 GIT binary patch literal 26443 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 literal 0 HcmV?d00001 diff --git a/packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-unsent-messages-sending-linux.png b/packages/shared-components/playwright/snapshots/room-roomstatusbarview--with-unsent-messages-sending-linux.png new file mode 100644 index 0000000000000000000000000000000000000000..0d4c8f288530aba14e08f14dd2c463900e783672 GIT binary patch literal 18665 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: ReactElement { +}: PropsWithChildren>): ReactElement { const classes = classNames(styles.banner, className); - const icon = useMemo(() => { + const icon = useMemo((): ReactElement => { switch (type) { case "critical": - return ; + return ; case "info": - return ; + return ; case "success": - return ; + return ; default: - return ; + return ; } - }, [type, props]); + }, [type]); return (
diff --git a/packages/shared-components/src/i18n/strings/en_EN.json b/packages/shared-components/src/i18n/strings/en_EN.json index d5521dfcf8..ce72683f8a 100644 --- a/packages/shared-components/src/i18n/strings/en_EN.json +++ b/packages/shared-components/src/i18n/strings/en_EN.json @@ -8,6 +8,7 @@ "explore_rooms": "Explore rooms", "pause": "Pause", "play": "Play", + "retry": "Retry", "search": "Search" }, "left_panel": { @@ -15,9 +16,24 @@ }, "room": { "status_bar": { - "history_visible": "This room has been configured so that new members can read history. Learn More" + "delete_all": "Delete all", + "exceeded_resource_limit_description": "Please contact your service administrator to continue using the service.", + "exceeded_resource_limit_title": "Your message wasn't sent because this homeserver has exceeded a resource limit.", + "failed_to_create_room_title": "Could not start a chat with this user", + "history_visible": "This room has been configured so that new members can read history. Learn More", + "homeserver_blocked_title": "Your message wasn't sent because this homeserver has been blocked by its administrator.", + "monthly_user_limit_reached_title": "Your message wasn't sent because this homeserver has hit its Monthly Active User Limit.", + "requires_consent_agreement_title": "You can't send any messages until you review and agree to our terms and conditions.", + "retry_all": "Retry all", + "select_messages_to_retry": "You can select all or individual messages to retry or delete", + "server_connectivity_lost_description": "Sent messages will be stored until your connection has returned.", + "server_connectivity_lost_title": "Connectivity to the server has been lost.", + "some_messages_not_sent": "Some of your messages have not been sent" } }, + "terms": { + "tac_button": "Review terms and conditions" + }, "time": { "about_day_ago": "about a day ago", "about_hour_ago": "about an hour ago", diff --git a/packages/shared-components/src/index.ts b/packages/shared-components/src/index.ts index 346f92ef35..7b9162a3f7 100644 --- a/packages/shared-components/src/index.ts +++ b/packages/shared-components/src/index.ts @@ -17,6 +17,7 @@ export * from "./event-tiles/TextualEventView"; export * from "./message-body/MediaBody"; export * from "./pill-input/Pill"; export * from "./pill-input/PillInput"; +export * from "./room/RoomStatusBar"; export * from "./rich-list/RichItem"; export * from "./rich-list/RichList"; export * from "./room-list/RoomListSearchView"; diff --git a/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.module.css b/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.module.css new file mode 100644 index 0000000000..b0e85609b6 --- /dev/null +++ b/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.module.css @@ -0,0 +1,11 @@ +.container { + color: var(--cpd-color-text-primary); + svg { + /* Ensure button icons are primary too */ + color: var(--cpd-color-text-primary) !important; + } +} + +.description { + color: var(--cpd-color-text-secondary); +} diff --git a/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.stories.tsx b/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.stories.tsx new file mode 100644 index 0000000000..38f8d86f1d --- /dev/null +++ b/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.stories.tsx @@ -0,0 +1,105 @@ +/* + * Copyright (c) 2025 Element Creations Ltd. + * + * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial + * Please see LICENSE files in the repository root for full details. + */ +import { type Meta, type StoryFn } from "@storybook/react-vite"; +import React, { type JSX } from "react"; +import { fn } from "storybook/test"; + +import { useMockedViewModel } from "../../useMockedViewModel"; +import { + RoomStatusBarState, + RoomStatusBarView, + type RoomStatusBarViewActions, + type RoomStatusBarViewSnapshot, +} from "./RoomStatusBarView"; + +type RoomStatusBarProps = RoomStatusBarViewSnapshot & RoomStatusBarViewActions; + +const RoomStatusBarViewWrapper = ({ + onResendAllClick, + onDeleteAllClick, + onRetryRoomCreationClick, + onTermsAndConditionsClicked, + ...rest +}: RoomStatusBarProps): JSX.Element => { + const vm = useMockedViewModel(rest, { + onResendAllClick, + onDeleteAllClick, + onRetryRoomCreationClick, + onTermsAndConditionsClicked, + }); + return ; +}; + +export default { + title: "room/RoomStatusBarView", + component: RoomStatusBarViewWrapper, + tags: ["autodocs"], + argTypes: {}, + args: { + onResendAllClick: fn(), + onDeleteAllClick: fn(), + onRetryRoomCreationClick: fn(), + onTermsAndConditionsClicked: fn(), + }, +} as Meta; + +const Template: StoryFn = (args) => ; + +/** + * Rendered when the client has lost connection with the server. + */ +export const WithConnectionLost = Template.bind({}); +WithConnectionLost.args = { + state: RoomStatusBarState.ConnectionLost, +}; + +/** + * Rendered when the client needs the user to consent to some terms and conditions before + * they can perform any room actions. + */ +export const WithConsentLink = Template.bind({}); +WithConsentLink.args = { + state: RoomStatusBarState.NeedsConsent, + consentUri: "#example", +}; + +/** + * Rendered when the server has hit a usage limit and is forbidding the user from performing + * any actions in the room. There is an optional parameter to link to an admin to contact. + */ +export const WithResourceLimit = Template.bind({}); +WithResourceLimit.args = { + state: RoomStatusBarState.ResourceLimited, + resourceLimit: "hs_disabled", + adminContactHref: "#example", +}; + +/** + * Rendered when the client has some unsent messages in the room, stored locally. + */ +export const WithUnsentMessages = Template.bind({}); +WithUnsentMessages.args = { + state: RoomStatusBarState.UnsentMessages, + isResending: false, +}; + +/** + * Rendered when the client has some unsent messages in the room, stored locally and is + * trying to send them. + */ +export const WithUnsentMessagesSending = Template.bind({}); +WithUnsentMessagesSending.args = { + state: RoomStatusBarState.UnsentMessages, + isResending: true, +}; +/** + * Rendered when a local room has failed to be created. + */ +export const WithLocalRoomRetry = Template.bind({}); +WithLocalRoomRetry.args = { + state: RoomStatusBarState.LocalRoomFailed, +}; diff --git a/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.test.tsx b/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.test.tsx new file mode 100644 index 0000000000..22b9204ab0 --- /dev/null +++ b/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.test.tsx @@ -0,0 +1,69 @@ +/* + * Copyright (c) 2025 Element Creations Ltd. + * + * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial + * Please see LICENSE files in the repository root for full details. + */ + +import React from "react"; +import { render } from "jest-matrix-react"; +import { composeStories } from "@storybook/react-vite"; +import userEvent from "@testing-library/user-event"; + +import * as stories from "./RoomStatusBarView.stories.tsx"; + +const { WithConnectionLost, WithConsentLink, WithResourceLimit, WithUnsentMessages, WithLocalRoomRetry } = + composeStories(stories); + +describe("RoomStatusBarView", () => { + it("renders connection lost", () => { + const { container } = render(); + expect(container).toMatchSnapshot(); + }); + it("renders resource limit error", () => { + const { container } = render(); + expect(container).toMatchSnapshot(); + }); + it("renders consent link", () => { + const { container, getByRole } = render(); + expect(container).toMatchSnapshot(); + + const button = getByRole("link"); + expect(button.getAttribute("href")).toEqual("#example"); + }); + it("renders unsent messages", async () => { + const { container } = render( + , + ); + expect(container).toMatchSnapshot(); + }); + it("renders unsent messages and deletes all", async () => { + const onDeleteAllClick = jest.fn(); + const { container, getByRole } = render(); + expect(container).toMatchSnapshot(); + + const button = getByRole("button", { name: "Delete all" }); + await userEvent.click(button); + expect(onDeleteAllClick).toHaveBeenCalled(); + }); + it("renders unsent messages and resends all", async () => { + const onResendAllClick = jest.fn(); + const { container, getByRole } = render(); + expect(container).toMatchSnapshot(); + + const button = getByRole("button", { name: "Retry all" }); + await userEvent.click(button); + expect(onResendAllClick).toHaveBeenCalled(); + }); + it("renders local room error", async () => { + const onRetryRoomCreationClick = jest.fn(); + const { container, getByRole } = render( + , + ); + expect(container).toMatchSnapshot(); + + const button = getByRole("button", { name: "Retry" }); + await userEvent.click(button); + expect(onRetryRoomCreationClick).toHaveBeenCalled(); + }); +}); diff --git a/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.tsx b/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.tsx new file mode 100644 index 0000000000..2472aeeade --- /dev/null +++ b/packages/shared-components/src/room/RoomStatusBar/RoomStatusBarView.tsx @@ -0,0 +1,310 @@ +/* + * Copyright (c) 2025 Element Creations Ltd. + * + * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial + * Please see LICENSE files in the repository root for full details. + */ + +import React, { useCallback, useId, type JSX } from "react"; +import { RestartIcon, DeleteIcon } from "@vector-im/compound-design-tokens/assets/web/icons"; +import { Button, InlineSpinner, Text } from "@vector-im/compound-web"; + +import styles from "./RoomStatusBarView.module.css"; +import { useViewModel } from "../../useViewModel"; +import { type ViewModel } from "../../viewmodel"; +import { useI18n } from "../../utils/i18nContext"; +import { Banner } from "../../composer/Banner"; +export interface RoomStatusBarViewActions { + /** + * Called when the user clicks on the 'resend all' button in the 'unsent messages' bar. + */ + onResendAllClick?: () => Promise; + + /** + * Called when the user clicks on the 'cancel all' button in the 'unsent messages' bar. + */ + onDeleteAllClick?: () => void; + + /** + * Called when the user clicks on the 'Retry' button in the 'failed to start chat' bar. + */ + onRetryRoomCreationClick?: () => void; + + /** + * Called when the user clicks on the 'Review Terms and Conditions' button. + */ + onTermsAndConditionsClicked?: () => void; +} + +export const RoomStatusBarState = { + /** + * Connectivity to the homeserver has been lost. The user can not take any actions + * until the connection is restored. + */ + ConnectionLost: "ConnectionLost", + /** + * The homeserver has indiciated the user needs to consent to the Terms and Conditions + * before they can send a message. + */ + NeedsConsent: "NeedsConsent", + /** + * The homeserver has indiciated that messages can not be sent due to a resource limit + * being reached. The user may use the given admin contact details. + */ + ResourceLimited: "ResourceLimited", + /** + * There are messages stored locally that previously failed to send that the user + * may now retry or delete. + */ + UnsentMessages: "UnsentMessages", + /** + * There was an error creating a room. The user may retry creation. + */ + LocalRoomFailed: "LocalRoomFailed", +} as const; + +export interface RoomStatusBarNotVisible { + state: null; +} + +export interface RoomStatusBarNoConnection { + state: "ConnectionLost"; +} + +export interface RoomStatusBarConsentState { + state: "NeedsConsent"; + consentUri: string; +} + +export interface RoomStatusBarResourceLimitedState { + state: "ResourceLimited"; + resourceLimit: "monthly_active_user" | "hs_disabled" | string; + adminContactHref?: string; +} + +export interface RoomStatusBarUnsentMessagesState { + state: "UnsentMessages"; + isResending: boolean; +} +export interface RoomStatusBarLocalRoomError { + state: "LocalRoomFailed"; +} + +export type RoomStatusBarViewSnapshot = + | RoomStatusBarNoConnection + | RoomStatusBarConsentState + | RoomStatusBarResourceLimitedState + | RoomStatusBarUnsentMessagesState + | RoomStatusBarLocalRoomError + | RoomStatusBarNotVisible; + +/** + * The view model for RoomStatusBarView. + */ +export type RoomStatusBarViewModel = ViewModel & RoomStatusBarViewActions; + +interface RoomStatusBarViewProps { + /** + * The view model for the banner. + */ + vm: RoomStatusBarViewModel; +} + +/** + * A component to alert to a failure in the context of a room. + * + * @example + * ```tsx + * + * ``` + */ +export function RoomStatusBarView({ vm }: Readonly): JSX.Element | null { + const { translate: _t } = useI18n(); + const snapshot = useViewModel(vm); + const bannerTitleId = useId(); + + const deleteAllClick = useCallback>( + (ev) => { + ev.preventDefault(); + vm.onDeleteAllClick?.(); + }, + [vm], + ); + + const resendClick = useCallback>( + (ev) => { + ev.preventDefault(); + void vm.onResendAllClick?.(); + }, + [vm], + ); + + const retryRoomCreationClick = useCallback>( + (ev) => { + ev.preventDefault(); + vm.onRetryRoomCreationClick?.(); + }, + [vm], + ); + + const termsAndConditionsClicked = useCallback>(() => { + // Allow the link to go through. + vm.onTermsAndConditionsClicked?.(); + }, [vm]); + + if (snapshot.state === null) { + // Nothing to show! + return null; + } + + switch (snapshot.state) { + case RoomStatusBarState.ConnectionLost: + return ( + +
+ + {_t("room|status_bar|server_connectivity_lost_title")} + + + {_t("room|status_bar|server_connectivity_lost_description")} + +
+
+ ); + case RoomStatusBarState.NeedsConsent: + return ( + + {_t("terms|tac_button")} + + } + > +
+ + {_t("room|status_bar|requires_consent_agreement_title")} + +
+
+ ); + case RoomStatusBarState.ResourceLimited: + return ( + + Contact admin + + ) + } + > +
+ + {{ + monthly_active_user: _t("room|status_bar|monthly_user_limit_reached_title"), + hs_disabled: _t("room|status_bar|homeserver_blocked_title"), + }[snapshot.resourceLimit] || _t("room|status_bar|exceeded_resource_limit_title")} + + + {_t("room|status_bar|exceeded_resource_limit_description")} + +
+
+ ); + case RoomStatusBarState.LocalRoomFailed: + return ( + + {_t("action|retry")} + + } + > + + {_t("room|status_bar|failed_to_create_room_title")} + + + ); + case RoomStatusBarState.UnsentMessages: + return ( + + ) : ( + <> + {vm.onDeleteAllClick && ( + + )} + {vm.onResendAllClick && ( + + )} + + ) + } + aria-labelledby={bannerTitleId} + > +
+ + {_t("room|status_bar|some_messages_not_sent")} + + + {_t("room|status_bar|select_messages_to_retry")} + +
+
+ ); + default: + // We should never get into this state. + return null; + } +} diff --git a/packages/shared-components/src/room/RoomStatusBar/__snapshots__/RoomStatusBarView.test.tsx.snap b/packages/shared-components/src/room/RoomStatusBar/__snapshots__/RoomStatusBarView.test.tsx.snap new file mode 100644 index 0000000000..b25238dff3 --- /dev/null +++ b/packages/shared-components/src/room/RoomStatusBar/__snapshots__/RoomStatusBarView.test.tsx.snap @@ -0,0 +1,520 @@ +// Jest Snapshot v1, https://jestjs.io/docs/snapshot-testing + +exports[`RoomStatusBarView renders connection lost 1`] = ` +
+ +`; + +exports[`RoomStatusBarView renders consent link 1`] = ` +
+ +
+`; + +exports[`RoomStatusBarView renders local room error 1`] = ` +
+ +
+`; + +exports[`RoomStatusBarView renders resource limit error 1`] = ` +
+ +
+`; + +exports[`RoomStatusBarView renders unsent messages 1`] = ` +
+ +
+`; + +exports[`RoomStatusBarView renders unsent messages and deletes all 1`] = ` +
+ +
+`; + +exports[`RoomStatusBarView renders unsent messages and resends all 1`] = ` +
+ +
+`; diff --git a/packages/shared-components/src/room/RoomStatusBar/index.ts b/packages/shared-components/src/room/RoomStatusBar/index.ts new file mode 100644 index 0000000000..43f1bfebc2 --- /dev/null +++ b/packages/shared-components/src/room/RoomStatusBar/index.ts @@ -0,0 +1,8 @@ +/* + * Copyright (c) 2025 Element Creations Ltd. + * + * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial + * Please see LICENSE files in the repository root for full details. + */ + +export * from "./RoomStatusBarView"; diff --git a/playwright/e2e/room/room-status-bar.spec.ts b/playwright/e2e/room/room-status-bar.spec.ts index 249aa6e9d5..78d5c49a30 100644 --- a/playwright/e2e/room/room-status-bar.spec.ts +++ b/playwright/e2e/room/room-status-bar.spec.ts @@ -83,6 +83,13 @@ test.describe("Room Status Bar", () => { const banner = page.getByRole("region", { name: "Room status bar" }); await expect(banner).toBeVisible({ timeout: 15000 }); await expect(banner).toMatchScreenshot("consent.png"); + + // Click consent + await banner.getByRole("link", { name: "View Terms and Conditions" }).click(); + await page.unroute("**/_matrix/client/**/send**"); + // Should now be allowed to retry. + await banner.getByRole("button", { name: "Retry all" }).click(); + await expect(banner).not.toBeVisible(); }, ); test.describe("Message fails to send", () => { @@ -161,7 +168,7 @@ test.describe("Room Status Bar", () => { await composer.fill("Hello"); await composer.press("Enter"); - const banner = page.getByText("!Some of your messages have"); + const banner = page.getByRole("status", { name: "Could not start a chat with this user" }); await expect(banner).toBeVisible(); await expect(banner).toMatchScreenshot("local_room_create_failed.png"); diff --git a/playwright/snapshots/room/room-status-bar.spec.ts/connectivity-lost-linux.png b/playwright/snapshots/room/room-status-bar.spec.ts/connectivity-lost-linux.png index 106f16403c8d7176857c0208269d901351484f50..0568892b397ffbf21035103db803013798ceeca0 100644 GIT binary patch literal 12452 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 t%>FmJN73KcArLIwv|9?uUKc~DS@ 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 LvLfZ*^!@%H!@RO6 literal 15218 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 diff --git a/playwright/snapshots/room/room-status-bar.spec.ts/local-room-create-failed-linux.png b/playwright/snapshots/room/room-status-bar.spec.ts/local-room-create-failed-linux.png index a8fe32646e3cc2c464952b8f554c6242e1c49f69..304a425466670e65750349bfdecec4a087bdb81a 100644 GIT binary patch literal 8394 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 literal 5965 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 b4oC$^ptiYpxn=$@39G59r&6QzGV*@_4;qCp diff --git a/playwright/snapshots/room/room-status-bar.spec.ts/message-failed-linux.png b/playwright/snapshots/room/room-status-bar.spec.ts/message-failed-linux.png index cccc5fb6757d750a7531257b2f5090aaaa6b2570..fe23d40790a07f49733f6e90af3996ebc285c1bb 100644 GIT binary patch literal 16999 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 E0D%@k_W%F@ literal 11561 zcmch7cT`hN6esGZeu9EZ2LT18gf30G(tGcrNtGIDp@WKmbSa@%=>!N6Ak@$V3{@a> zNGQ^KPpBKeJ$ufcv;XeyKX2~b_vX#Kd3Wyo?r&~{mWJXZVme|XBBDpiN^&|xM0d~x z+4A4pgsaEh3T`5z$3)6<@AP~!x99I0Q5d$}+n+}2X>Wij#EDNM*>j&KPx;4G_qayW z#kBVP#8j~=Jn@%(Yuy$3;V}ug>czi5j(3{R+RBX$r_2mlE_??s{C!%Q;r4bznQ6Rd zSpxQU4FE{wEkb8RpMLb({w;~xxgI0`(+vExNdKQg?f;2F?GctaLXZ>q62hqmpuF>6 z-w(U2s&S^V6)~ZqpFldkx}CL3T%Nq-%l)@x)Vwr9WS8pbX6)wdoG>MyB9LMG z+|t3?f z*1+UCCq|I)g5h;18Zh$(%UAjZ-qh2ORZfJ9lfHTOQlCD!_xUPGu8MMAF#gIPu99T= zcS;tdqYHIPrHs}c+{KPyr8OQD_QNR6EPbgU8S3frEwHC$3U9B=_?PARXj|*S0Kmxi zJz7rH#Zf#LBWxem7ye)r>#ap)@7B2O=YF9Knn&ZZ_Q}T0ZF9qbyH|E`Y%j>^fMxv#wc>5=c799V$JFJ^`Z+P@I zpG}XKxdVllPqurirW+ajOS0J~#VE;rG^>Wj6ikX;awD7rcORa`I*ZE$!&wEaeD)*&iE?9g`L*$u}|dCBx}dj zSSOoHEthBvHgq;ue%aJWgZnhI^(BLcP7nXwJ&y`bck$Y7u-gesPcItdpsI+fu3Hpz ze4Z*+-Hx1aejbcNxX;{;V}ft*;P0I8H+crks`N73-j4+=?NucayB3pv;qRhFwks`j z?n-`l!IpkQ_IxzTJU_vO+^^zH;;!l%7iVUPnr%Q{E@;~>S%Y23I<|ABUa8WF(IoMX z9nN@-47vLHh%_fTeLg2yyXF$7%4-Qq+%d>r#ztbB#k&@1ra2T$qDk+W_nwxObIo)| z8+E!&oATK*Gkm{G2E6mgspRgls}Ku>e)_K!-o)1MyplHRdDf+ow6T$3k-S#F@jP49 zBIvZ`5GA0W{p~s_E~jrev!4k%|E|XKE~T~91DFM`t!H$JVzBQYi=-!B!8$8{BEy1U zeJH9+zF28Tn!E2t5G)QqRt+P=lJvN|U6v6b&g|At0Ohn%_hF{(NXnP0DbRw~UTM(k zC8i>HALPkE7HV(8*o{?1!d`n(ObK!M0*FYPZ7Kb@$mKewFj|*k1H8`NFbJ377OpS| z#%=xbM`ct^Q(Ut<^WS9N{2~j7b8){xO7%cpz6RX956WRQP&{*Qaoob6>}y{)Xm>t> z>S^XgoCiUz;M_O=QVpg4XgEg%?7dK@Jt)|Sj7ss5Z2ot3z!KvABvAUD+gi5Yok@^^ zY3yR$<&b0WzsS(>rUe2!el&KT zaOzuC*N+rz38U(-Q7&7WJE&3v`5O1EdOw1_{3y1WaW+UBr4mQ{Tdbki)1xeMRq1_X z+kARBgL`0qCAX+qvp}u#eX~M}K^{_Y%wdX@Yp`Kta396W9*aob)pERyR^t~6GKjSt zrMWIyESm($u_y>IyDg4$@G6cSu$opUC6}uOaTwP|^9S(#rp-F3J94(S??{c`Bs*U! z#iiJ0ie-Pn!{2bX7D7dSfwzT`y3tITqgi>GGmObEW^v>S{jmzazNqm~dS*I#scpF@UhgCV!JpMkzsmtgrdgz)DNKLa8q35h%~7dOUwHR{zv^IgB3@-S znYXxRHE_3XuubQ&L~A`amB{hS+TiSk*DoCgevM2}Re1a`aEP8z(O&uDgH8kFDChZXwj zZbqb3Vt>-3HOD+0s#eX!R1jAjarlhc+{&hU#mtCl8CLv={f{ENLJ<^*c*>AtAD6lA6=#MO45+=@IaAt{1`m8 zl4Oc~-hD!!3D~WrGg)S7JD67fXIkG+moW1X*?#cA*deH<+$i$$DU z=BAHPvdPbJn-5nuL3LYEqq9}+`P{kQPy)bcmy@SO>H{414IK8VbfeZ*BiJ-3qiH%X zz(ieE{7fM`n?H76GK#AlOmg50IhT~jzCx4TGX!-^+vHO=gq|d$m~b7XW-*gzpYX@fZlmi%)DiYK`x)I8rlHoG%PS~ zP^aITl?u}x+1X*^NvVcgUyH8j#v$K)G-ytpm7br56&ied(hSTz#e5w za<+&icQsGg83Rk*(a?)OA@9s;Du+x@wvn zUeuj#ZdPi?yrlQ$CoCPLI4Kptk;?arwf*Q%vGsp}5siVKHFCwUGQytQQYyl)c6Wu7 zmC9gcWkv8fZ)msccVv%ti{p1>vad9g*v?AuKU9R~|$V!yr?05=qpc z)imW8cUPHKtp0$3+YV@l;v^=aJF7}E<76c+ ztpE2fZ$hP$qY@9>-~0Z2pwV^juuTJX+SZzpXlskQC}I#wI!BHwoY?j9gC zWTSf%E$zuy_vvs~QXYNR(IycQ@m^dUHJrJ8US|Vg*MREES-fA7774=_9~8FjS^i`; z&j_Y#18MsHc`)*a_7W*+tZ|AS3vHV#ZGZfwqUL25#c#OfsK+ zDT{}cc2sNT0VUazi7xX)JJXOw_n2)8T~ZB}heF$I^`A!6?-1dl-H+tLJBL*ZH+cZ( zWWM3;MFz=Kp;6qX*TpYyrXP56j8vwo<6jRA()lHE9V{|N$}UpBhP$7iedtP+2Wwzp zPO@z~40=Vi`DunOzs3sCz=H=aSM(7-NB7%!u*i%OEkIq{Xq_=HnYYEB*xmHNUSu1i zgrC35bYI^OXO7(heH-nt2czc#U`4W#Exq+v+TE*{Sj#^!*r2k5d)~$&A*!}dNJoI(shi9Y+U-AyJWs-1u^R-w&nrV|wTBP4A zZf@MN!U56&v;<&3|Fbg#MTU+Xx^zeDWo&JAF`+e2*Ld)Y)^i4!7DlszsN~lm# z;7*zyO#(Vt)|P#9!G`K_+0<5}P@oritoF?Moa%rr1~PCHs>6CkosNZy!_0vAirE

j&&Lfs5y8ns_L4oDCP#2TKpk}qM`*(u>JVwQC+c2<0sV!|qH+u}b0Vfi^JruK7V|?ynbtvkornb^tX@y7xEEShw@Z!f~S z7fUGImr3xOT?mz=;s!56q!ZbR=QUdb;=FO;NH6Z`T@Sk|)y6(vi+GnA6|-d}0-v(~ zjtdq{WAxj2Nje-;{Gym;lXkBR@87ppgg`%0g{bbSY9Tz^Xc=wXs> z39lIR&!@>|Ei`X&KSIG%n5zpCfE)G5N2(METcn=+Q@^CMz2IEApzVp4?$t5s!<(F? zxmO4K{AB}N1j-@p=3Yn1qH`SGkB%;nbbLhd@OzOGwo6|Cf$y=bIi5^wtDKj=agH7_H#)Z)SY zfEBA?mKzC0mfeXi6-pIqB}|%eWAIl6lYj5di{XyR?_@7OQPvSGL(x#Uie02yj9(0m9NZ^kk$h+Has|mW;Kg>T%@D z%};JZyNq73ryDcrg9hGOlO+a08=Gd{yV4c<%k$#2*=)tHiVNZxCdOHBZo$SmQ~a-3 z1z1mAd)w`r`t{h8_^Z9e5J!~;#(}cZ-A*TmFznbd%xPqMIox~lUhhR*pM-yWUqF0c zviq|smW7aR3CTGJfsLBCLTB!GgLF#uMD|{eYMRYl{GKF096EIA#KhhX+|4Xg#hE1H zSKkol<9s23dWY%u(Zih>BXdRwi-v+Ol6v1))c40%HdIm-$$-wlgyZq|p<~#pQ?^pT z^X*KPlj^-_{v77uu0r$lsfq-en8_Q798v-@U4Z8zjo9v=aGoZZ7rbgy%Yl1l?80Ce zn~k8r)5}8BJe=2#|K4lP0GO$XUziayiKLH;H*-`sAoGTuy2rGQGZB^3rWAP1Jc!Hs zb|X7eoJGUCY6I#mv9P|{MTL+tu??Ek=pPxg{}BOg8^g=aZ_y}oz}9bfLfZD$hqA9( zp&xOpAE##is7sVJ%V#&aU%1L-ndnzy1C%Ct1nuA4U0bRdHjhkHvEkLVkPb@zp#^{d zUWK28k~(rH><CeS&m}&eStvQ=D4G|6?%J~pA!{k-6KdJTg2!j zNIKvuXyV3QLQ|#nseiF?zDa0TH4pgusLoSUp;lA8F=s!s@}AGN2kpB;J>g0Vf@9;D zpUz^46kw8Jzz9M08=k;Ou_8-MzJ7XEl$*abd@ijfKPN&slil38Mhf1kBZw<|HGBCi zs+b>Ow*inOg|0KnxT1mk)H=v#e>v@aQ7w!0>ne8P3|*nNE%bD?&E@=0;uTXNV~s+c z`KCmp`T>8?krx<{#zrNcR13$mg>7~AIGkt9L8OuL#xrXlgBW-^7^nstz3t%?zWkw6{L!$G*g`4 zkz!&=-<1kxPJOfDv*OdN-@hMKeX)ryYw=Z_N?hY8bpZK!IvY2%XWiHQK<#;D|3)Pp zbw+dvqfic)AOy$(xwXu05*n z3$B(;yvK;PVDMXbd3PncJTp*nh%vI^J0z=EycsB(;t1)#X*`p=Z0&7ic0(67{0?Cw z&o04ot52J-rs#ePfMhGT!mqhE~F;3&)yj0!c>7ks6Sbbq`FFAV!XQ9 zLi$QT8sLw#$SOWOtiYnhJxYTQuuA2RDr&a7#X=TfZ3 z%m|Xk zR%9?7ZFnv&ZVkc|OABY{cMjFdh^COY#8erEyWF76-B8S3c1*%R_ z27K{JIpvO3FrV|l)v9z;z^jS(U5w!A^y=O)qnTE#G)RYke~Jg~6ie>AtTME3(BYg= z-?!UR2!oi&TNT8oFYe)m#GbhY^~dt@gpcLA*3FD_zA7x>w|J?lO6){=9ouXO_3Q4G zyrT1rbvx4dVLzxM^Z7dC_`{@LnO3Asy?>}q<lHnp&n!KhD@R+?pfpW2-8-$V2?-{7|F_d4WYx6v2HHeF})s)D6N?O6A(;V%7ra z&mTys+Znj-pR%YFy1$M4bQ_=XdKcgCrk&zCWdsbGY|Da-h)@Mm5j=EUPNNw9B3lA; zv#R`}NMPlaxV#rriRGvfmBo$6G9~Es?xbrFLdQ%Nm0?GrmffDpy8SC2Bk8{`mFlsC zJJ_16e2;Xdr3IM?UhKDfo1N`qL<2XIHdKo`$$Mk0rN()qs9lWOhLRF`V;Qe}&pnsn z626xOPHP&lQR3{Sv-O#ik^JyzlmQp;^rGHn;Ksv#C==wmVPYB8*s<$r#R`VyK`gW;XKx*)qog6nLd z2GPbiT5*Ca=xqEoYvwk8*+EK*?RZQdtWpV0*L z<~(2a+3q+XKC;R4%49AuZqrq2uq72H|0G*>U+i9~j=4$*A^>fAxfkv>TaPa>4#K%@ zetR!_XSTkszTUVQe3Ht){Ey6H6g96f=wWPZY^8at9~OD#=7PB&%m==1A%PutBxA*Jp`&7ex$bOU+lkzbYi5-riv-8cto*ZWcaa z&w0aWTEx7=lG5z3+ygJx zq=v({CR*?7>mvd@k5|mZ!I)NmgfhISOEKE>qn7l^k)xX0uUH0j>BiV-vH!670m79# zQ#!6lQ9;f$I!Gj&O++L`_{hhmK#rMK66_ovi=_cUp@vp6;N6Cs1@q+|^)`Cp=n46( z`1xkf2ac21Q`Pw-RNSRNL}k&RP?9wcPTgkh{FB`=w$~C8Qc_3=2#V50^A-#Y4NX_M z4yFm%&&|zkj)QW=qx4vTH6KQH11|*0*M>8IWqPF`F)tH@ojME?_(4SvJ^efDg=V${ zBj1PbMGwdGWVN)=p$L}RCeL#_)Mz0kr@;(EQ&gq1gwKAi>ZGf6Z`_*u$+OD-;ETad z85}$I+Y=W3XvhB5!Kc+ezY(%C-s`yt-;JMHt76n%$w4mUQ{bunMZdEd$ojf;y-Q3~ z)KQu4+FBZX`{=Ac)ME|2J9Ti0hf7_ZGl+Wn^bDjypn7>BHvOyWBPscuhNTjJn)5s* z*3CkDzW5$>c6F}rp;3vPhOiO;Tu1F?e_vnuEJ@i}8KB&wr%xEK#Uv&9O6GGrLQ;5) zf0&^&eUCiPmg~7Q?%ck;fli`INJtnhwvVg&wJg)oER}b4aT>}XnwglmwY4Yx@%MA7 z98Johp&=C|rCb+_YR9_z0!*Mfv0fPL$nv`Lkxa^)1dEpS`TPrS*>Eb%V=2Z>GNPhV zUFhp8eoG!<;bcj%x~CB@QM_YgqXI@;_4y%LaBJnfPra$~7sBcrarh>Ro#kG9*FBP8 zvtKnef`xpPaHINE=@O=+_&x|PHM(-XNytf7R;DkRW40v}Vak*9CdgDh&Lq$O6ugJ= zm_c)FY%np_Bmd#$Gaw>**z-3pz_B}WdwY8jSkGh9@>0--t=lwRiS~yI1aO~}q3F|V z(5|UEieAJuiNj3H=V-NNrEdp!q&XjIV{2Dw(ikxMhsk?yo|D2PQ_>?$`~FW`2_8^? zJ+@daOMxUh<_ZYRw(2{y2xgG5QCi2e^6*q1tqtWxC@U+&gR)0J3!hkeV<8+s@Mc`% zY`v4nN%4lu?c1J-BBJ=oh)I|QXs*WVV6?CeG_N8+H~sd+%6@2F`s2conSWmj@6A{e zlhBxlyL)*>g#&#Zs`*pY+OTG}m{(7ETJV+E5@uc;53JS8)7pMGE#!_a=?W*^q^bnM zvgMeI3WiFsI)K83^*yY~g_D)l(wD}gFj6L@fTy>+ySrmqhj{58CPLbK_u0xq>wQuw z4YfB<9QHADKoJm+QLWENg2hCo@zs7u7sHEYg*f^)t7(uY&AN-Z7^KOK#dSQr4mwfU z%y@B@uSiC+CnN^VJKdfu+#0c7bakZ^xp!XxA7Z~ctZR5Z{QWmYSzyh%f>)ZFFg{#a zJwrJED8_ZZNi$oJgOjs)A5dGDB^>BysrCC0hc3HshI{U4P z8wUu`7z*NgC|nC8F;oDWgF;GXvEvYM6Xwx-0x~19d!HBd$+D|yoE}|jf{cbwC!9@| z{lZ>#ojABYY04UFi8!#*duujuL9Xd~j|_i0QwK%A5_MgYJNJ_mHhBJ6XR;0g(QmzX zk|F2AZEbyhs@Nh}on~Bzo$_h*OE!_-dZTKNu_Ep8LL)9Qk5x1R8>pySWIk$85il$- z@6aC}9*%hM@VG=js)^qJWH)eUQ(pz}q&K$Cb*yJ>EUIf!OA{XnxyQsHYc>yG9jHSf z){gE@2n%aIC695=x2r}UfUK?On?cxt0j|N1@2R5XvwkNh8-&?8W2^JwaDnd9uoyaQ zvv*wmI@*FQJcj1otWllGiSVt@O`#4Bg0D6Q9L}GSdldcv7U~qLIt5F*UHZ)C*6ZD$ zG2i@0pI=3mv+xznq%}-sb!A0VOjJ9rJTD>J+^a-)Zhn4#e0&@pOPw+3I$cv}`eJxs z06p9CG>wZ_M6*;+C*`u~Q3tx)+y^!i54XGWo9Rc#@2&qy{a#}3Z(}3(*78%)t&OJ7 zt9C0}!M$RlqWC&j^$vu?(W+++1vNd;htkiVw{$;m{);p)+x(fH`{A}*ySaVnx@0* zg9UwQH0Iuj+3J0fe+b6HX&0Nff*_V4%F1PEL&2<-55qkAk!EnQ zVkC9(P#awzA#RwiG;3Z{R!(}d;bdZx9(B}wk!5C@Ii@4MU)~oj0`du{1ivjClZG=* zAwWk(F_d$21aG9isK8@rPqEoEaS3?5Unq9wm$1~W8qFvGUOV0C*qYS!D{5DK!p$b$ zTa0gBTV5v>_dOE3`rQ$tXC(egVENH_&X0&y&TbX;)6pog5o+#K5O5%NDOQdvnUga5 zeN)sRR-qV;PC>t+I5>%2|E<#|{+uaiI0f~GmNre|mgcMhdKKMK4$Mx#9y^SM#Xa*n zJ*Ks|IkUoU9ecVke1Ji?96%omd3AMGhchlV$2slU>{UiRH?2xup5<&-AGTf%RF$rr z2*VJFv+-0;Plga;5!cZIMVNW$S$aj*{ER+SBS*?O?+d+4>FXPp^1A>K2*&s=;acoU z#nUq}Y_G?<1?5alfv#)^c#3D&sflXU#b{LfP=hsXLk zH>QuyA7TAJ+RyZ-4Bb4_^Xy5;f~dEyHgT8Q{-6I3d7;2ze$)TeD;`q&~>K4ZT560{c|V! z-LKS7O@Iwe=6D_xKHfJzU1ZW~^|iGUbWcj@+iK$i*&X)YQZJQ~8F@db6^ranAFjnv zD=Rl;^){^zXNlu`IUXJ6kEiY_@+)lcBx@JXrljL=)!W;VsF$x@fUQ2-`$D(S9iaCP z2m6a%1Rxh3&}Q&TB^f>O`P^1$So%F&^e`ZOo4t>Gq>WzW-eifk_0+fcW8bY+^=bUZ zzV(KS`C*sM$#;5{&&$2hMHq|CO`fVr_C~4TQ|Dpil}uiDozvt*rHS%NR0?}#MT<jFr9GyVBcP z_>**a`0B()0N*?;mV*hUnVD1oSeLw$@|7h-D@ayCg2JERFMbz)+>L#VXaZy7;@W%` zTY~9N)H5LfgBgT9nU_e9SzFLn&!c%`cG~;(kLId^7(xN@?4Ztu>J%RHKkmM-8}&-H zw0H_AT>At@m?V7od=`lMb}5c4$}1eIZ|7C1TR!*7*BKT(;f(z zJlf``v`-Fp+Hch+6P^70^;I$M!_o+gVv)K&cA1@m_%+6c!idmUwVWE$P`0GUQIGnv z*O=M%?r*d1$Y}$Zc^2L$NfC(0JI(+&IF$FkGX~#GWQ2q`O_UffY*1ZS0K-EW)YX)7 z2Mbh*)3rWWTg%#06LxO^Rn+M&h8t2g9EFp}mID-$>ERj{Z((~jTrh-fc_>rLj4OWM zC*X7FT_NYiR)xUJMqghvBomTGOIM={uT_Yl8{5sjR}iXo2SBme|J<{xv={L;bVTmF zln_mo@>)=thq_j*``g)3S>xW0Lj!wBfe7b`%*x9epOJKZs3*04DnhfL-p%cJZEMYN zp%}a~1H#sGb8-R!kb5wTNu;%+Fz_ar_~DLID`e#N?DNes6C&3~&%6#nuvt1^>4^@6B>mIGc zbu0qZ3w}55g#IvxoBw^PQ>b$F#>-^?{E-x9@bv30ouuotsO}#TaJyl%Mk`Tn8!V=k zAQvU5rwhaD>+-B9?$^OJQ~4b5ur^`PDDF>0n}nk;4UC=}yjm_=I|crHi$Y|L*QA`G z;GnukJyq`J-rau&u6-2{yOPAz`%d%eL-#K+Odg$o$Wm?`dWNH@c$}wyG(w}GQBjb?f z=lUjL`{wzs)`o^DRD=2UcYgg^r4fCwKTaEP==Uqp7K! zpDTcx>3qnW_Rp~z8li@HKxk~1n4(3KV6KJq-xXK^ysrh-$Pz1b$PY_1Ha2S}n5o|4 zp|J48c$r~a@E$V7uw%lB{PA0RD{IBL%~@!QQ|V||Se)gpWgY_{$Fo4FdT2wh3D*VN(_0vz>~-GYb9t zx3 div[role="alert"] { - /* cheat some basic alignment */ - display: flex; - align-items: center; - min-height: 70px; - margin: 12px; - padding-left: 16px; - background-color: $header-panel-bg-color; - border-radius: 4px; - } - - .mx_RoomStatusBar_unsentBadge { - margin-right: 12px; - - .mx_NotificationBadge { - /* Override sizing from the default badge */ - width: 24px !important; - height: 24px !important; - border-radius: 24px !important; - - .mx_NotificationBadge_count { - font-size: $font-16px !important; /* override default */ - } - } - } - - .mx_RoomStatusBar_unsentTitle { - color: $alert; - font-size: $font-15px; - } - - .mx_RoomStatusBar_unsentDescription { - font-size: $font-12px; - } - - .mx_RoomStatusBar_unsentButtonBar { - flex-grow: 1; - text-align: right; - margin-right: 22px; - color: $muted-fg-color; - - .mx_AccessibleButton { - padding: 5px 10px; - padding-left: 30px; /* 18px for the icon, 2px margin to text, 10px regular padding */ - display: inline-block; - position: relative; - user-select: none; - - & + .mx_AccessibleButton { - border-left: 1px solid $resend-button-divider-color; - } - - svg { - left: 10px; /* inset for regular button padding */ - - width: 18px; - height: 18px; - vertical-align: middle; - color: $muted-fg-color; - } - } - - .mx_InlineSpinner { - vertical-align: middle; - margin-right: 5px; - top: 1px; /* just to help the vertical alignment be slightly better */ - - & + span { - margin-right: 10px; /* same margin/padding as the rightmost button */ - } - } - } -} - -.mx_RoomStatusBar_connectionLostBar svg { - padding-left: 10px; - padding-right: 10px; - vertical-align: middle; - float: left; -} - -.mx_RoomStatusBar_connectionLostBar_title { - color: $alert; -} - -.mx_RoomStatusBar_connectionLostBar_desc { - color: $primary-content; - font-size: $font-13px; - opacity: 0.5; - padding-bottom: 20px; -} - -.mx_RoomStatusBar_resend_link { - color: $primary-content !important; - text-decoration: underline !important; - cursor: pointer; -} - -.mx_RoomStatusBar_typingBar { - height: 50px; - line-height: 50px; - - color: $primary-content; - opacity: 0.5; - overflow-y: hidden; - display: block; -} - -.mx_MatrixChat_useCompactLayout { - .mx_RoomStatusBar:not(.mx_RoomStatusBar_unsentMessages) { - min-height: 40px; - } - - .mx_RoomStatusBar_indicator { - margin-top: 10px; - } - - .mx_RoomStatusBar_typingBar { - height: 40px; - line-height: 40px; - } -} diff --git a/src/RoomNotifs.ts b/src/RoomNotifs.ts index d5254d523d..2db2cf2158 100644 --- a/src/RoomNotifs.ts +++ b/src/RoomNotifs.ts @@ -13,16 +13,38 @@ import { PushRuleActionName, PushRuleKind, TweakName, + EventStatus, } from "matrix-js-sdk/src/matrix"; -import type { IPushRule, Room, MatrixClient } from "matrix-js-sdk/src/matrix"; +import type { IPushRule, Room, MatrixClient, MatrixEvent } from "matrix-js-sdk/src/matrix"; import { NotificationLevel } from "./stores/notifications/NotificationLevel"; -import { getUnsentMessages } from "./components/structures/RoomStatusBar"; import { doesRoomHaveUnreadMessages, doesRoomOrThreadHaveUnreadMessages } from "./Unread"; import { EffectiveMembership, getEffectiveMembership, isKnockDenied } from "./utils/membership"; import SettingsStore from "./settings/SettingsStore"; import { getMarkedUnreadState } from "./utils/notifications"; +/** + * Gets all pending events in a room that have a status of `EventStatus.NOT_SENT` + * and belong to the current thread, if specified. + * @param room The room to check. + * @param threadId The thread to check. If not specified, no thread filtering is performed. + * @returns An array of unsent matrix events. + */ +export function getUnsentMessages(room: Room, threadId?: string): MatrixEvent[] { + if (!room) { + return []; + } + return room.getPendingEvents().filter(function (ev) { + if (ev.status !== EventStatus.NOT_SENT) { + return false; + } + if (threadId && threadId !== ev.threadRootId) { + return false; + } + return true; + }); +} + export enum RoomNotifState { AllMessagesLoud = "all_messages_loud", AllMessages = "all_messages", diff --git a/src/components/structures/RoomStatusBar.tsx b/src/components/structures/RoomStatusBar.tsx deleted file mode 100644 index d9889342b1..0000000000 --- a/src/components/structures/RoomStatusBar.tsx +++ /dev/null @@ -1,297 +0,0 @@ -/* -Copyright 2024 New Vector Ltd. -Copyright 2015-2021 The Matrix.org Foundation C.I.C. - -SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial -Please see LICENSE files in the repository root for full details. -*/ - -import React, { type JSX, type ReactNode } from "react"; -import { - ClientEvent, - EventStatus, - type MatrixError, - type MatrixEvent, - type Room, - RoomEvent, - type SyncState, - type SyncStateData, -} from "matrix-js-sdk/src/matrix"; -import { RestartIcon, WarningIcon, DeleteIcon } from "@vector-im/compound-design-tokens/assets/web/icons"; - -import { _t, _td } from "../../languageHandler"; -import Resend from "../../Resend"; -import dis from "../../dispatcher/dispatcher"; -import { messageForResourceLimitError } from "../../utils/ErrorUtils"; -import { Action } from "../../dispatcher/actions"; -import { StaticNotificationState } from "../../stores/notifications/StaticNotificationState"; -import AccessibleButton from "../views/elements/AccessibleButton"; -import InlineSpinner from "../views/elements/InlineSpinner"; -import MatrixClientContext from "../../contexts/MatrixClientContext"; -import { RoomStatusBarUnsentMessages } from "./RoomStatusBarUnsentMessages"; -import ExternalLink from "../views/elements/ExternalLink"; - -const STATUS_BAR_HIDDEN = 0; -const STATUS_BAR_EXPANDED = 1; -const STATUS_BAR_EXPANDED_LARGE = 2; - -export function getUnsentMessages(room: Room, threadId?: string): MatrixEvent[] { - if (!room) { - return []; - } - return room.getPendingEvents().filter(function (ev) { - const isNotSent = ev.status === EventStatus.NOT_SENT; - const belongsToTheThread = threadId === ev.threadRootId; - return isNotSent && (!threadId || belongsToTheThread); - }); -} - -interface IProps { - // the room this statusbar is representing. - room: Room; - - // true if the room is being peeked at. This affects components that shouldn't - // logically be shown when peeking, such as a prompt to invite people to a room. - isPeeking?: boolean; - // callback for when the user clicks on the 'resend all' button in the - // 'unsent messages' bar - onResendAllClick?: () => void; - - // callback for when the user clicks on the 'cancel all' button in the - // 'unsent messages' bar - onCancelAllClick?: () => void; - - // callback for when the user clicks on the 'invite others' button in the - // 'you are alone' bar - onInviteClick?: () => void; - - // callback for when we do something that changes the size of the - // status bar. This is used to trigger a re-layout in the parent - // component. - onResize?: () => void; - - // callback for when the status bar can be hidden from view, as it is - // not displaying anything - onHidden?: () => void; - - // callback for when the status bar is displaying something and should - // be visible - onVisible?: () => void; -} - -interface IState { - syncState: SyncState | null; - syncStateData: SyncStateData | null; - unsentMessages: MatrixEvent[]; - isResending: boolean; -} - -export default class RoomStatusBar extends React.PureComponent { - private unmounted = false; - public static contextType = MatrixClientContext; - declare public context: React.ContextType; - - public constructor(props: IProps, context: React.ContextType) { - super(props, context); - - this.state = { - syncState: this.context.getSyncState(), - syncStateData: this.context.getSyncStateData(), - unsentMessages: getUnsentMessages(this.props.room), - isResending: false, - }; - } - - public componentDidMount(): void { - this.unmounted = false; - - const client = this.context; - client.on(ClientEvent.Sync, this.onSyncStateChange); - client.on(RoomEvent.LocalEchoUpdated, this.onRoomLocalEchoUpdated); - - this.checkSize(); - } - - public componentDidUpdate(): void { - this.checkSize(); - } - - public componentWillUnmount(): void { - this.unmounted = true; - // we may have entirely lost our client as we're logging out before clicking login on the guest bar... - const client = this.context; - if (client) { - client.removeListener(ClientEvent.Sync, this.onSyncStateChange); - client.removeListener(RoomEvent.LocalEchoUpdated, this.onRoomLocalEchoUpdated); - } - } - - private onSyncStateChange = (state: SyncState, prevState: SyncState | null, data?: SyncStateData): void => { - if (state === "SYNCING" && prevState === "SYNCING") { - return; - } - if (this.unmounted) return; - this.setState({ - syncState: state, - syncStateData: data ?? null, - }); - }; - - private onResendAllClick = (): void => { - Resend.resendUnsentEvents(this.props.room).then(() => { - this.setState({ isResending: false }); - }); - this.setState({ isResending: true }); - dis.fire(Action.FocusSendMessageComposer); - }; - - private onCancelAllClick = (): void => { - Resend.cancelUnsentEvents(this.props.room); - dis.fire(Action.FocusSendMessageComposer); - }; - - private onRoomLocalEchoUpdated = (ev: MatrixEvent, room: Room): void => { - if (room.roomId !== this.props.room.roomId) return; - const messages = getUnsentMessages(this.props.room); - this.setState({ - unsentMessages: messages, - isResending: messages.length > 0 && this.state.isResending, - }); - }; - - // Check whether current size is greater than 0, if yes call props.onVisible - private checkSize(): void { - if (this.getSize()) { - if (this.props.onVisible) this.props.onVisible(); - } else { - if (this.props.onHidden) this.props.onHidden(); - } - } - - // We don't need the actual height - just whether it is likely to have - // changed - so we use '0' to indicate normal size, and other values to - // indicate other sizes. - private getSize(): number { - if (this.shouldShowConnectionError()) { - return STATUS_BAR_EXPANDED; - } else if (this.state.unsentMessages.length > 0 || this.state.isResending) { - return STATUS_BAR_EXPANDED_LARGE; - } - return STATUS_BAR_HIDDEN; - } - - private shouldShowConnectionError(): boolean { - // no conn bar trumps the "some not sent" msg since you can't resend without - // a connection! - // There's one situation in which we don't show this 'no connection' bar, and that's - // if it's a resource limit exceeded error: those are shown in the top bar. - const errorIsMauError = Boolean( - this.state.syncStateData && - this.state.syncStateData.error && - this.state.syncStateData.error.name === "M_RESOURCE_LIMIT_EXCEEDED", - ); - return this.state.syncState === "ERROR" && !errorIsMauError; - } - - private getUnsentMessageContent(): JSX.Element { - const unsentMessages = this.state.unsentMessages; - - let title: ReactNode; - - let consentError: MatrixError | null = null; - let resourceLimitError: MatrixError | null = null; - for (const m of unsentMessages) { - if (m.error && m.error.errcode === "M_CONSENT_NOT_GIVEN") { - consentError = m.error; - break; - } else if (m.error && m.error.errcode === "M_RESOURCE_LIMIT_EXCEEDED") { - resourceLimitError = m.error; - break; - } - } - if (consentError) { - title = _t( - "room|status_bar|requires_consent_agreement", - {}, - { - consentLink: (sub) => ( - - {sub} - - ), - }, - ); - } else if (resourceLimitError) { - title = messageForResourceLimitError( - resourceLimitError.data.limit_type, - resourceLimitError.data.admin_contact, - { - "monthly_active_user": _td("room|status_bar|monthly_user_limit_reached"), - "hs_disabled": _td("room|status_bar|homeserver_blocked"), - "": _td("room|status_bar|exceeded_resource_limit"), - }, - ); - } else { - title = _t("room|status_bar|some_messages_not_sent"); - } - - let buttonRow = ( - <> - - - {_t("room|status_bar|delete_all")} - - - - {_t("room|status_bar|retry_all")} - - - ); - if (this.state.isResending) { - buttonRow = ( - <> - - {/* span for css */} - {_t("forward|sending")} - - ); - } - - return ( - - ); - } - - public render(): React.ReactNode { - if (this.shouldShowConnectionError()) { - return ( -

-
-
- -
-
- {_t("room|status_bar|server_connectivity_lost_title")} -
-
- {_t("room|status_bar|server_connectivity_lost_description")} -
-
-
-
-
- ); - } - - if (this.state.unsentMessages.length > 0 || this.state.isResending) { - return this.getUnsentMessageContent(); - } - - return null; - } -} diff --git a/src/components/structures/RoomStatusBarUnsentMessages.tsx b/src/components/structures/RoomStatusBarUnsentMessages.tsx deleted file mode 100644 index 0845f2550a..0000000000 --- a/src/components/structures/RoomStatusBarUnsentMessages.tsx +++ /dev/null @@ -1,36 +0,0 @@ -/* -Copyright 2024 New Vector Ltd. -Copyright 2022 The Matrix.org Foundation C.I.C. - -SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial -Please see LICENSE files in the repository root for full details. -*/ - -import React, { type ReactElement, type ReactNode } from "react"; - -import { type StaticNotificationState } from "../../stores/notifications/StaticNotificationState"; -import NotificationBadge from "../views/rooms/NotificationBadge"; - -interface RoomStatusBarUnsentMessagesProps { - title: ReactNode; - description?: string; - notificationState: StaticNotificationState; - buttons: ReactElement; -} - -export const RoomStatusBarUnsentMessages = (props: RoomStatusBarUnsentMessagesProps): ReactElement => { - return ( -
-
-
- -
-
-
{props.title}
- {props.description &&
{props.description}
} -
-
{props.buttons}
-
-
- ); -}; diff --git a/src/components/structures/RoomView.tsx b/src/components/structures/RoomView.tsx index 904ada4090..7f86f5d28c 100644 --- a/src/components/structures/RoomView.tsx +++ b/src/components/structures/RoomView.tsx @@ -16,6 +16,7 @@ import React, { type ReactNode, type RefObject, type JSX, + useEffect, } from "react"; import classNames from "classnames"; import { @@ -45,7 +46,7 @@ import { debounce, throttle } from "lodash"; import { CryptoEvent } from "matrix-js-sdk/src/crypto-api"; import { type ViewRoomOpts } from "@matrix-org/react-sdk-module-api/lib/lifecycles/RoomViewLifecycle"; import { type RoomViewProps } from "@element-hq/element-web-module-api"; -import { RestartIcon } from "@vector-im/compound-design-tokens/assets/web/icons"; +import { RoomStatusBarView, useCreateAutoDisposedViewModel } from "@element-hq/web-shared-components"; import shouldHideEvent from "../../shouldHideEvent"; import { _t } from "../../languageHandler"; @@ -92,7 +93,6 @@ import { type IOpts } from "../../createRoom"; import EditorStateTransfer from "../../utils/EditorStateTransfer"; import ErrorDialog from "../views/dialogs/ErrorDialog"; import UploadBar from "./UploadBar"; -import RoomStatusBar from "./RoomStatusBar"; import MessageComposer from "../views/rooms/MessageComposer"; import JumpToBottomButton from "../views/rooms/JumpToBottomButton"; import TopUnreadMessagesBar from "../views/rooms/TopUnreadMessagesBar"; @@ -112,10 +112,8 @@ import { LocalRoom, LocalRoomState } from "../../models/LocalRoom"; import { createRoomFromLocalRoom } from "../../utils/direct-messages"; import NewRoomIntro from "../views/rooms/NewRoomIntro"; import EncryptionEvent from "../views/messages/EncryptionEvent"; -import { StaticNotificationState } from "../../stores/notifications/StaticNotificationState"; import { isLocalRoom } from "../../utils/localRoom/isLocalRoom"; import { type ShowThreadPayload } from "../../dispatcher/payloads/ShowThreadPayload"; -import { RoomStatusBarUnsentMessages } from "./RoomStatusBarUnsentMessages"; import { LargeLoader } from "./LargeLoader"; import { isVideoRoom } from "../../utils/video-rooms"; import { SDKContext } from "../../contexts/SDKContext"; @@ -137,6 +135,7 @@ import { DeclineAndBlockInviteDialog } from "../views/dialogs/DeclineAndBlockInv import { type FocusMessageSearchPayload } from "../../dispatcher/payloads/FocusMessageSearchPayload.ts"; import { isRoomEncrypted } from "../../hooks/useIsEncrypted"; import { type RoomViewStore } from "../../stores/RoomViewStore.tsx"; +import { RoomStatusBarViewModel } from "../../viewmodels/room/RoomStatusBar.ts"; const DEBUG = false; const PREVENT_MULTIPLE_JITSI_WITHIN = 30_000; @@ -317,33 +316,11 @@ function LocalRoomView(props: LocalRoomViewProps): ReactElement { encryptionTile = ; } - const onRetryClicked = (): void => { - // eslint-disable-next-line react-compiler/react-compiler - room.state = LocalRoomState.NEW; - defaultDispatcher.dispatch({ - action: "local_room_event", - roomId: room.roomId, - }); - }; - let statusBar: ReactElement | null = null; let composer: ReactElement | null = null; if (room.isError) { - const buttons = ( - - - {_t("action|retry")} - - ); - - statusBar = ( - - ); + statusBar = ; } else { composer = ( ); } +/** + * Wrap a RoomStatusBarView and ViewModel into one component, for usage with legacy React components. + */ +function RoomStatusBarWrappedView(props: ConstructorParameters[0]): ReactElement { + const vm = useCreateAutoDisposedViewModel(() => new RoomStatusBarViewModel(props)); + useEffect(() => { + // Note: We need to tell the parent component whether the viewmodel expects to render anything + // (see onStatusBarVisible). This is ugly, but works. + if ("onVisible" in props) { + // Initial setup + if (vm.getSnapshot().state !== null) { + props.onVisible(); + } else { + props.onHidden?.(); + } + vm.subscribe(() => { + if (vm.getSnapshot().state !== null) { + props.onVisible?.(); + } else { + props.onHidden?.(); + } + }); + } + }, [vm, props]); + + return ; +} export class RoomView extends React.Component { // We cache the latest computed e2eStatus per room to show as soon as we switch rooms otherwise defaulting to @@ -1687,14 +1691,6 @@ export class RoomView extends React.Component { } } - private onInviteClick = (): void => { - // open the room inviter - defaultDispatcher.dispatch({ - action: "view_invite", - roomId: this.getRoomId(), - }); - }; - private onJoinButtonClicked = (): void => { // If the user is a ROU, allow them to transition to a PWLU if (this.context.client?.isGuest()) { @@ -2401,10 +2397,8 @@ export class RoomView extends React.Component { } else if (!this.state.search) { isStatusAreaExpanded = this.state.statusBarVisible; statusBar = ( - diff --git a/src/components/structures/TimelinePanel.tsx b/src/components/structures/TimelinePanel.tsx index 665ca6f677..aeda2237e0 100644 --- a/src/components/structures/TimelinePanel.tsx +++ b/src/components/structures/TimelinePanel.tsx @@ -29,6 +29,7 @@ import { Thread, ThreadEvent, ReceiptType, + EventStatus, } from "matrix-js-sdk/src/matrix"; import { debounce } from "lodash"; import { logger } from "matrix-js-sdk/src/logger"; @@ -1004,6 +1005,7 @@ class TimelinePanel extends React.Component { lastReadEventIndex: number | null, ): lastReadEvent is MatrixEvent { if (!lastReadEvent) return false; + if (lastReadEvent.status === EventStatus.NOT_SENT) return false; // We want to avoid sending out read receipts when we are looking at // events in the past which are before the latest RR. diff --git a/src/i18n/strings/en_EN.json b/src/i18n/strings/en_EN.json index 8d1ae17ea2..e431fff11d 100644 --- a/src/i18n/strings/en_EN.json +++ b/src/i18n/strings/en_EN.json @@ -2128,18 +2128,6 @@ }, "this_room_button": "Search this room" }, - "status_bar": { - "delete_all": "Delete all", - "exceeded_resource_limit": "Your message wasn't sent because this homeserver has exceeded a resource limit. Please
contact your service administrator to continue using the service.", - "homeserver_blocked": "Your message wasn't sent because this homeserver has been blocked by its administrator. Please contact your service administrator to continue using the service.", - "monthly_user_limit_reached": "Your message wasn't sent because this homeserver has hit its Monthly Active User Limit. Please contact your service administrator to continue using the service.", - "requires_consent_agreement": "You can't send any messages until you review and agree to our terms and conditions.", - "retry_all": "Retry all", - "select_messages_to_retry": "You can select all or individual messages to retry or delete", - "server_connectivity_lost_description": "Sent messages will be stored until your connection has returned.", - "server_connectivity_lost_title": "Connectivity to the server has been lost.", - "some_messages_not_sent": "Some of your messages have not been sent" - }, "unknown_status_code_for_timeline_jump": "unknown status code", "unread_notifications_predecessor": { "one": "You have %(count)s unread notification in a prior version of this room.", diff --git a/src/stores/notifications/RoomNotificationState.ts b/src/stores/notifications/RoomNotificationState.ts index af873f712e..44a62b1307 100644 --- a/src/stores/notifications/RoomNotificationState.ts +++ b/src/stores/notifications/RoomNotificationState.ts @@ -141,7 +141,6 @@ export class RoomNotificationState extends NotificationState implements IDestroy private updateNotificationState(): void { const snapshot = this.snapshot(); - const { level, symbol, count, invited } = RoomNotifs.determineUnreadState( this.room, undefined, diff --git a/src/viewmodels/room/RoomStatusBar.ts b/src/viewmodels/room/RoomStatusBar.ts new file mode 100644 index 0000000000..799b3c4cec --- /dev/null +++ b/src/viewmodels/room/RoomStatusBar.ts @@ -0,0 +1,223 @@ +/* + * Copyright (c) 2025 Element Creations Ltd. + * + * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial + * Please see LICENSE files in the repository root for full details. + */ + +import { + BaseViewModel, + RoomStatusBarState, + type RoomStatusBarViewModel as RoomStatusBarViewModelInterface, + type RoomStatusBarViewSnapshot, +} from "@element-hq/web-shared-components"; +import { + ClientEvent, + SyncState, + type MatrixClient, + type Room, + type MatrixError, + RoomEvent, + EventStatus, +} from "matrix-js-sdk/src/matrix"; + +import { MatrixClientPeg } from "../../MatrixClientPeg"; +import Resend from "../../Resend"; +import { Action } from "../../dispatcher/actions"; +import dis from "../../dispatcher/dispatcher"; +import { LocalRoom, LocalRoomState } from "../../models/LocalRoom"; + +interface PropsWithRoom { + room: Room | LocalRoom; +} +interface PropsWithVisibility extends PropsWithRoom { + /** + * Called when the bar becomes visible. + */ + onVisible: () => void; + /** + * Called when the bar becomes hidden. + */ + onHidden: () => void; +} + +type Props = PropsWithRoom | PropsWithVisibility; + +export class RoomStatusBarViewModel + extends BaseViewModel + implements RoomStatusBarViewModelInterface +{ + /** + * Check if the room has any unread messages. If it does, we should render the specific message + * depending on the kind of error encountered when sending them. + * + * Because a room can contain multiple unsent messages, the resultant state is based on the + * "most important" error to show. + * + * @param room The room being viewed. + * @param hasClickedTermsAndConditions Whether the terms and conditions button has just been pressed. + * @returns A snapshot if an error should be visible, or null if not. + */ + private static readonly determineStateForUnreadMessages = ( + room: Room, + hasClickedTermsAndConditions: boolean, + ): RoomStatusBarViewSnapshot => { + const unsentMessages = room.getPendingEvents().filter((ev) => ev.status === EventStatus.NOT_SENT); + if (unsentMessages.length === 0) { + return { + state: null, + }; + } + if (hasClickedTermsAndConditions) { + // The user has just clicked (and we *assume* accepted) the terms and contitions, so show them the retry buttons. + // If the user has not accepted the terms, we will just prompt the same error again anyway. + return { + state: RoomStatusBarState.UnsentMessages, + isResending: false, + }; + } + + // Filter through the errors and find the most important error. + let resourceLimitError: MatrixError | null = null; + for (const m of unsentMessages) { + if (m.error?.errcode === "M_CONSENT_NOT_GIVEN") { + // This is the most important thing to show, so break here if we find one. + return { + state: RoomStatusBarState.NeedsConsent, + consentUri: m.error.data.consent_uri, + }; + } + if (m.error?.errcode === "M_RESOURCE_LIMIT_EXCEEDED") { + resourceLimitError = m.error; + } + } + if (resourceLimitError) { + return { + state: RoomStatusBarState.ResourceLimited, + resourceLimit: resourceLimitError.data.limit_type ?? "", + adminContactHref: resourceLimitError.data.admin_contact, + }; + } + // Otherwise, we know there are unsent messages but the error is not special. + return { + state: RoomStatusBarState.UnsentMessages, + isResending: false, + }; + }; + + private static readonly computeSnapshot = ( + room: Room, + client: MatrixClient, + isResending: boolean, + hasClickedTermsAndConditions: boolean, + ): RoomStatusBarViewSnapshot => { + const isLocalRoomAndIsError = (room as LocalRoom)["isError"]; + if (isLocalRoomAndIsError !== undefined) { + return { + // Local room errors can only be about failed room creation. + state: isLocalRoomAndIsError ? RoomStatusBarState.LocalRoomFailed : null, + }; + } + + // If we're in the process of resending, always show a resending state so we don't flicker. + if (isResending) { + return { + state: RoomStatusBarState.UnsentMessages, + isResending, + }; + } + + const syncState = client.getSyncState(); + + // Highest priority. + // A no-connection bar trumps all else, as you won't be able to resend or do anything! + if (syncState === SyncState.Error) { + const syncData = client.getSyncStateData(); + if (syncData?.error?.name === "M_RESOURCE_LIMIT_EXCEEDED") { + // There's one situation in which we don't show this 'no connection' bar, and that's + // if it's a M_RESOURCE_LIMIT_EXCEEDED error: those are shown as a toast by LoggedInView. + return { + state: null, + }; + } + return { + state: RoomStatusBarState.ConnectionLost, + }; + } + + // Connection is good, so check room messages for any failures. + return this.determineStateForUnreadMessages(room, hasClickedTermsAndConditions); + }; + + private readonly client: MatrixClient; + + public constructor(props: Props) { + const client = MatrixClientPeg.safeGet(); + super(props, RoomStatusBarViewModel.computeSnapshot(props.room, client, false, false)); + this.client = client; + this.disposables.trackListener(client, ClientEvent.Sync, this.onClientSync); + this.disposables.trackListener(props.room, RoomEvent.LocalEchoUpdated, this.onRoomLocalEchoUpdated); + } + + private readonly onClientSync = (): void => { + this.setSnapshot(); + }; + + private readonly onRoomLocalEchoUpdated = (): void => { + this.setSnapshot(); + }; + + private isResending = false; + private hasClickedTermsAndConditions = false; + + private setSnapshot(): void { + this.snapshot.set( + RoomStatusBarViewModel.computeSnapshot( + this.props.room, + this.client, + this.isResending, + this.hasClickedTermsAndConditions, + ), + ); + // Reset `hasClickedTermsAndConditions` once the state has cleared. + if (this.hasClickedTermsAndConditions && !this.snapshot.current.state) { + this.hasClickedTermsAndConditions = false; + } + } + + public onTermsAndConditionsClicked = (): void => { + this.hasClickedTermsAndConditions = true; + this.setSnapshot(); + }; + + public onDeleteAllClick = (): void => { + Resend.cancelUnsentEvents(this.props.room); + dis.fire(Action.FocusSendMessageComposer); + this.setSnapshot(); + }; + + public onResendAllClick = async (): Promise => { + this.isResending = true; + this.setSnapshot(); + try { + await Resend.resendUnsentEvents(this.props.room); + dis.fire(Action.FocusSendMessageComposer); + } finally { + this.isResending = false; + this.setSnapshot(); + } + }; + + public onRetryRoomCreationClick = (): void => { + if (this.props.room instanceof LocalRoom === false) { + throw Error("Tried to recreate local room, but room was not local."); + } + + // This resets the local room state from error. + this.props.room.state = LocalRoomState.NEW; + dis.dispatch({ + action: "local_room_event", + roomId: this.props.room.roomId, + }); + }; +} diff --git a/test/test-utils/test-utils.ts b/test/test-utils/test-utils.ts index 043f4590a8..4dfd5e4de8 100644 --- a/test/test-utils/test-utils.ts +++ b/test/test-utils/test-utils.ts @@ -32,6 +32,7 @@ import { type GroupCall, HistoryVisibility, type ICreateRoomOpts, + type EventStatus, } from "matrix-js-sdk/src/matrix"; import { KnownMembership } from "matrix-js-sdk/src/types"; import { normalize } from "matrix-js-sdk/src/utils"; @@ -303,6 +304,7 @@ export function createTestClient(): MatrixClient { room_id: roomId, }); }), + resendEvent: jest.fn().mockResolvedValue({}), _unstable_sendDelayedEvent: jest.fn(), _unstable_sendDelayedStateEvent: jest.fn(), @@ -402,6 +404,7 @@ type MakeEventProps = MakeEventPassThruProps & { // eslint-disable-next-line camelcase prev_content?: IContent; unsigned?: IUnsigned; + status?: EventStatus; }; export const mkRoomCreateEvent = (userId: string, roomId: string, content?: IContent): MatrixEvent => { @@ -482,6 +485,9 @@ export function mkEvent(opts: MakeEventProps): MatrixEvent { getMxcAvatarUrl: () => {}, } as unknown as RoomMember; } + if (opts.status !== undefined) { + mxEvent.status = opts.status; + } return mxEvent; } @@ -702,7 +708,7 @@ export function mkStubRoom( getMembersWithMembership: jest.fn().mockReturnValue([]), getMxcAvatarUrl: () => "mxc://avatar.url/room.png", getMyMembership: jest.fn().mockReturnValue(KnownMembership.Join), - getPendingEvents: () => [] as MatrixEvent[], + getPendingEvents: jest.fn().mockReturnValue([]), getReceiptsForEvent: jest.fn().mockReturnValue([]), getRecommendedVersion: jest.fn().mockReturnValue(Promise.resolve("")), getThreads: jest.fn().mockReturnValue([]), diff --git a/test/unit-tests/RoomNotifs-test.ts b/test/unit-tests/RoomNotifs-test.ts index cff4ecef75..e514288a6c 100644 --- a/test/unit-tests/RoomNotifs-test.ts +++ b/test/unit-tests/RoomNotifs-test.ts @@ -26,10 +26,73 @@ import { RoomNotifState, getUnreadNotificationCount, determineUnreadState, + getUnsentMessages, } from "../../src/RoomNotifs"; import { NotificationLevel } from "../../src/stores/notifications/NotificationLevel"; import SettingsStore from "../../src/settings/SettingsStore"; import { MatrixClientPeg } from "../../src/MatrixClientPeg"; +import { mkThread } from "../test-utils/threads"; + +describe("getUnsentMessages", () => { + const ROOM_ID = "!roomId"; + let room: Room; + let event: MatrixEvent; + let client: MatrixClient; + beforeEach(() => { + client = stubClient(); + room = new Room(ROOM_ID, client, client.getUserId()!, { + pendingEventOrdering: PendingEventOrdering.Detached, + }); + event = mkEvent({ + event: true, + type: "m.room.message", + user: "@user1:server", + room: "!room1:server", + content: {}, + }); + event.status = EventStatus.NOT_SENT; + }); + + it("returns no unsent messages", () => { + expect(getUnsentMessages(room)).toHaveLength(0); + }); + + it("checks the event status", () => { + room.addPendingEvent(event, "123"); + + expect(getUnsentMessages(room)).toHaveLength(1); + event.status = EventStatus.SENT; + + expect(getUnsentMessages(room)).toHaveLength(0); + }); + + it("only returns events related to a thread", () => { + room.addPendingEvent(event, "123"); + + const { rootEvent, events } = mkThread({ + room, + client, + authorId: "@alice:example.org", + participantUserIds: ["@alice:example.org"], + length: 2, + }); + rootEvent.status = EventStatus.NOT_SENT; + room.addPendingEvent(rootEvent, rootEvent.getId()!); + for (const event of events) { + event.status = EventStatus.NOT_SENT; + room.addPendingEvent(event, Date.now() + Math.random() + ""); + } + + const pendingEvents = getUnsentMessages(room, rootEvent.getId()); + + expect(pendingEvents[0].threadRootId).toBe(rootEvent.getId()); + expect(pendingEvents[1].threadRootId).toBe(rootEvent.getId()); + expect(pendingEvents[2].threadRootId).toBe(rootEvent.getId()); + + // Filters out the non thread events + expect(pendingEvents.every((ev) => ev.getId() !== event.getId())).toBe(true); + }); +}); describe("RoomNotifs test", () => { let client: jest.Mocked; diff --git a/test/unit-tests/components/structures/RoomStatusBar-test.tsx b/test/unit-tests/components/structures/RoomStatusBar-test.tsx deleted file mode 100644 index 844ed8ab2d..0000000000 --- a/test/unit-tests/components/structures/RoomStatusBar-test.tsx +++ /dev/null @@ -1,150 +0,0 @@ -/* -Copyright 2024 New Vector Ltd. -Copyright 2022 The Matrix.org Foundation C.I.C. - -SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial -Please see LICENSE files in the repository root for full details. -*/ - -import React from "react"; -import { render } from "jest-matrix-react"; -import { - type MatrixClient, - PendingEventOrdering, - EventStatus, - type MatrixEvent, - Room, - MatrixError, -} from "matrix-js-sdk/src/matrix"; - -import RoomStatusBar, { getUnsentMessages } from "../../../../src/components/structures/RoomStatusBar"; -import MatrixClientContext from "../../../../src/contexts/MatrixClientContext"; -import { MatrixClientPeg } from "../../../../src/MatrixClientPeg"; -import { mkEvent, stubClient } from "../../../test-utils/test-utils"; -import { mkThread } from "../../../test-utils/threads"; - -describe("RoomStatusBar", () => { - const ROOM_ID = "!roomId:example.org"; - let room: Room; - let client: MatrixClient; - let event: MatrixEvent; - - beforeEach(() => { - jest.clearAllMocks(); - - stubClient(); - client = MatrixClientPeg.safeGet(); - client.getSyncStateData = jest.fn().mockReturnValue({}); - room = new Room(ROOM_ID, client, client.getUserId()!, { - pendingEventOrdering: PendingEventOrdering.Detached, - }); - event = mkEvent({ - event: true, - type: "m.room.message", - user: "@user1:server", - room: "!room1:server", - content: {}, - }); - event.status = EventStatus.NOT_SENT; - }); - - const getComponent = () => - render(, { - wrapper: ({ children }) => ( - {children} - ), - }); - - describe("getUnsentMessages", () => { - it("returns no unsent messages", () => { - expect(getUnsentMessages(room)).toHaveLength(0); - }); - - it("checks the event status", () => { - room.addPendingEvent(event, "123"); - - expect(getUnsentMessages(room)).toHaveLength(1); - event.status = EventStatus.SENT; - - expect(getUnsentMessages(room)).toHaveLength(0); - }); - - it("only returns events related to a thread", () => { - room.addPendingEvent(event, "123"); - - const { rootEvent, events } = mkThread({ - room, - client, - authorId: "@alice:example.org", - participantUserIds: ["@alice:example.org"], - length: 2, - }); - rootEvent.status = EventStatus.NOT_SENT; - room.addPendingEvent(rootEvent, rootEvent.getId()!); - for (const event of events) { - event.status = EventStatus.NOT_SENT; - room.addPendingEvent(event, Date.now() + Math.random() + ""); - } - - const pendingEvents = getUnsentMessages(room, rootEvent.getId()); - - expect(pendingEvents[0].threadRootId).toBe(rootEvent.getId()); - expect(pendingEvents[1].threadRootId).toBe(rootEvent.getId()); - expect(pendingEvents[2].threadRootId).toBe(rootEvent.getId()); - - // Filters out the non thread events - expect(pendingEvents.every((ev) => ev.getId() !== event.getId())).toBe(true); - }); - }); - - describe("", () => { - it("should render nothing when room has no error or unsent messages", () => { - const { container } = getComponent(); - expect(container.firstChild).toBe(null); - }); - - describe("unsent messages", () => { - it("should render warning when messages are unsent due to consent", () => { - const unsentMessage = mkEvent({ - event: true, - type: "m.room.message", - user: "@user1:server", - room: "!room1:server", - content: {}, - }); - unsentMessage.status = EventStatus.NOT_SENT; - unsentMessage.error = new MatrixError({ - errcode: "M_CONSENT_NOT_GIVEN", - data: { consent_uri: "terms.com" }, - }); - - room.addPendingEvent(unsentMessage, "123"); - - const { container } = getComponent(); - - expect(container).toMatchSnapshot(); - }); - - it("should render warning when messages are unsent due to resource limit", () => { - const unsentMessage = mkEvent({ - event: true, - type: "m.room.message", - user: "@user1:server", - room: "!room1:server", - content: {}, - }); - unsentMessage.status = EventStatus.NOT_SENT; - unsentMessage.error = new MatrixError({ - errcode: "M_RESOURCE_LIMIT_EXCEEDED", - data: { limit_type: "monthly_active_user" }, - }); - - room.addPendingEvent(unsentMessage, "123"); - - const { container } = getComponent(); - - expect(container).toMatchSnapshot(); - }); - }); - }); -}); diff --git a/test/unit-tests/components/structures/RoomStatusBarUnsentMessages-test.tsx b/test/unit-tests/components/structures/RoomStatusBarUnsentMessages-test.tsx deleted file mode 100644 index d608cb0627..0000000000 --- a/test/unit-tests/components/structures/RoomStatusBarUnsentMessages-test.tsx +++ /dev/null @@ -1,39 +0,0 @@ -/* -Copyright 2024 New Vector Ltd. -Copyright 2022 The Matrix.org Foundation C.I.C. - -SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial -Please see LICENSE files in the repository root for full details. -*/ - -import React from "react"; -import { render, screen } from "jest-matrix-react"; - -import { RoomStatusBarUnsentMessages } from "../../../../src/components/structures/RoomStatusBarUnsentMessages"; -import { StaticNotificationState } from "../../../../src/stores/notifications/StaticNotificationState"; - -describe("RoomStatusBarUnsentMessages", () => { - const title = "test title"; - const description = "test description"; - const buttonsText = "test buttons"; - const buttons =
{buttonsText}
; - - beforeEach(() => { - render( - , - ); - }); - - it("should render the values passed as props", () => { - screen.getByText(title); - screen.getByText(description); - screen.getByText(buttonsText); - // notification state - screen.getByText("!"); - }); -}); diff --git a/test/unit-tests/components/structures/__snapshots__/RoomStatusBar-test.tsx.snap b/test/unit-tests/components/structures/__snapshots__/RoomStatusBar-test.tsx.snap deleted file mode 100644 index 78a5a19aed..0000000000 --- a/test/unit-tests/components/structures/__snapshots__/RoomStatusBar-test.tsx.snap +++ /dev/null @@ -1,182 +0,0 @@ -// Jest Snapshot v1, https://jestjs.io/docs/snapshot-testing - -exports[`RoomStatusBar unsent messages should render warning when messages are unsent due to consent 1`] = ` -
-
-
-
-
- - ! - -
-
-
-
- - You can't send any messages until you review and agree to - - our terms and conditions - - - - - - . - -
-
- You can select all or individual messages to retry or delete -
-
-
-
- - - - Delete all -
-
- - - - Retry all -
-
-
-
-
-`; - -exports[`RoomStatusBar unsent messages should render warning when messages are unsent due to resource limit 1`] = ` -
-
-
-
-
- - ! - -
-
-
-
- Your message wasn't sent because this homeserver has exceeded a resource limit. Please contact your service administrator to continue using the service. -
-
- You can select all or individual messages to retry or delete -
-
-
-
- - - - Delete all -
-
- - - - Retry all -
-
-
-
-
-`; diff --git a/test/unit-tests/components/structures/__snapshots__/RoomView-test.tsx.snap b/test/unit-tests/components/structures/__snapshots__/RoomView-test.tsx.snap index 9003fbbd6d..acdb6b2be1 100644 --- a/test/unit-tests/components/structures/__snapshots__/RoomView-test.tsx.snap +++ b/test/unit-tests/components/structures/__snapshots__/RoomView-test.tsx.snap @@ -212,53 +212,61 @@ exports[`RoomView for a local room in state ERROR should match the snapshot 1`]
@@ -409,7 +417,7 @@ exports[`RoomView for a local room in state NEW should match the snapshot 1`] = >