MainLoopDriverTests.cs 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277
  1. using System;
  2. using System.Collections;
  3. using System.Collections.Generic;
  4. using System.Linq;
  5. using System.Threading;
  6. using Xunit;
  7. using Xunit.Abstractions;
  8. // Alias Console to MockConsole so we don't accidentally use Console
  9. using Console = Terminal.Gui.FakeConsole;
  10. namespace Terminal.Gui.DriverTests;
  11. public class MainLoopDriverTests {
  12. public MainLoopDriverTests (ITestOutputHelper output) => ConsoleDriver.RunningUnitTests = true;
  13. [Theory]
  14. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  15. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  16. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  17. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  18. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  19. public void MainLoop_Constructs_Disposes (Type driverType, Type mainLoopDriverType)
  20. {
  21. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  22. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  23. var mainLoop = new MainLoop (mainLoopDriver);
  24. // Check default values
  25. Assert.NotNull (mainLoop);
  26. Assert.Equal (mainLoopDriver, mainLoop.MainLoopDriver);
  27. Assert.Empty (mainLoop.IdleHandlers);
  28. Assert.Empty (mainLoop.Timeouts);
  29. Assert.False (mainLoop.Running);
  30. // Clean up
  31. mainLoop.Dispose ();
  32. // TODO: It'd be nice if we could really verify IMainLoopDriver.TearDown was called
  33. // and that it was actually cleaned up.
  34. Assert.Null (mainLoop.MainLoopDriver);
  35. Assert.Empty (mainLoop.IdleHandlers);
  36. Assert.Empty (mainLoop.Timeouts);
  37. Assert.False (mainLoop.Running);
  38. }
  39. [Theory]
  40. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  41. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  42. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  43. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  44. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  45. public void MainLoop_AddTimeout_ValidParameters_ReturnsToken (Type driverType, Type mainLoopDriverType)
  46. {
  47. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  48. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  49. var mainLoop = new MainLoop (mainLoopDriver);
  50. bool callbackInvoked = false;
  51. object token = mainLoop.AddTimeout (TimeSpan.FromMilliseconds (100), () => {
  52. callbackInvoked = true;
  53. return false;
  54. });
  55. Assert.NotNull (token);
  56. mainLoop.RunIteration (); // Run an iteration to process the timeout
  57. Assert.False (callbackInvoked); // Callback should not be invoked immediately
  58. Thread.Sleep (200); // Wait for the timeout
  59. mainLoop.RunIteration (); // Run an iteration to process the timeout
  60. Assert.True (callbackInvoked); // Callback should be invoked after the timeout
  61. mainLoop.Dispose ();
  62. }
  63. [Theory]
  64. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  65. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  66. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  67. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  68. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  69. public void MainLoop_RemoveTimeout_ValidToken_ReturnsTrue (Type driverType, Type mainLoopDriverType)
  70. {
  71. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  72. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  73. var mainLoop = new MainLoop (mainLoopDriver);
  74. object token = mainLoop.AddTimeout (TimeSpan.FromMilliseconds (100), () => false);
  75. bool result = mainLoop.RemoveTimeout (token);
  76. Assert.True (result);
  77. mainLoop.Dispose ();
  78. }
  79. [Theory]
  80. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  81. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  82. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  83. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  84. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  85. public void MainLoop_RemoveTimeout_InvalidToken_ReturnsFalse (Type driverType, Type mainLoopDriverType)
  86. {
  87. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  88. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  89. var mainLoop = new MainLoop (mainLoopDriver);
  90. bool result = mainLoop.RemoveTimeout (new object ());
  91. Assert.False (result);
  92. }
  93. [Theory]
  94. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  95. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  96. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  97. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  98. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  99. public void MainLoop_AddIdle_ValidIdleHandler_ReturnsToken (Type driverType, Type mainLoopDriverType)
  100. {
  101. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  102. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  103. var mainLoop = new MainLoop (mainLoopDriver);
  104. bool idleHandlerInvoked = false;
  105. bool IdleHandler ()
  106. {
  107. idleHandlerInvoked = true;
  108. return false;
  109. }
  110. var token = mainLoop.AddIdle (IdleHandler);
  111. Assert.NotNull (token);
  112. Assert.False (idleHandlerInvoked); // Idle handler should not be invoked immediately
  113. mainLoop.RunIteration (); // Run an iteration to process the idle handler
  114. Assert.True (idleHandlerInvoked); // Idle handler should be invoked after processing
  115. mainLoop.Dispose ();
  116. }
  117. [Theory]
  118. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  119. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  120. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  121. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  122. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  123. public void MainLoop_RemoveIdle_ValidToken_ReturnsTrue (Type driverType, Type mainLoopDriverType)
  124. {
  125. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  126. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  127. var mainLoop = new MainLoop (mainLoopDriver);
  128. bool IdleHandler () => false;
  129. var token = mainLoop.AddIdle (IdleHandler);
  130. bool result = mainLoop.RemoveIdle (token);
  131. Assert.True (result);
  132. mainLoop.Dispose ();
  133. }
  134. [Theory]
  135. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  136. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  137. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  138. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  139. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  140. public void MainLoop_RemoveIdle_InvalidToken_ReturnsFalse (Type driverType, Type mainLoopDriverType)
  141. {
  142. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  143. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  144. var mainLoop = new MainLoop (mainLoopDriver);
  145. bool result = mainLoop.RemoveIdle (() => false);
  146. Assert.False (result);
  147. mainLoop.Dispose ();
  148. }
  149. [Theory]
  150. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  151. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  152. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  153. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  154. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  155. public void MainLoop_RunIteration_ValidIdleHandler_CallsIdleHandler (Type driverType, Type mainLoopDriverType)
  156. {
  157. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  158. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  159. var mainLoop = new MainLoop (mainLoopDriver);
  160. bool idleHandlerInvoked = false;
  161. var idleHandler = () => {
  162. idleHandlerInvoked = true;
  163. return false;
  164. };
  165. mainLoop.AddIdle (idleHandler);
  166. mainLoop.RunIteration (); // Run an iteration to process the idle handler
  167. Assert.True (idleHandlerInvoked);
  168. mainLoop.Dispose ();
  169. }
  170. [Theory]
  171. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  172. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  173. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  174. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  175. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  176. public void MainLoop_CheckTimersAndIdleHandlers_NoTimersOrIdleHandlers_ReturnsFalse (Type driverType, Type mainLoopDriverType)
  177. {
  178. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  179. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  180. var mainLoop = new MainLoop (mainLoopDriver);
  181. bool result = mainLoop.CheckTimersAndIdleHandlers (out int waitTimeout);
  182. Assert.False (result);
  183. Assert.Equal (-1, waitTimeout);
  184. mainLoop.Dispose ();
  185. }
  186. [Theory]
  187. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  188. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  189. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  190. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  191. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  192. public void MainLoop_CheckTimersAndIdleHandlers_TimersActive_ReturnsTrue (Type driverType, Type mainLoopDriverType)
  193. {
  194. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  195. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  196. var mainLoop = new MainLoop (mainLoopDriver);
  197. mainLoop.AddTimeout (TimeSpan.FromMilliseconds (100), () => false);
  198. bool result = mainLoop.CheckTimersAndIdleHandlers (out int waitTimeout);
  199. Assert.True (result);
  200. Assert.True (waitTimeout >= 0);
  201. mainLoop.Dispose ();
  202. }
  203. [Theory]
  204. [InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  205. [InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  206. [InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  207. [InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  208. //[InlineData (typeof (ANSIDriver), typeof (AnsiMainLoopDriver))]
  209. public void MainLoop_CheckTimersAndIdleHandlers_IdleHandlersActive_ReturnsTrue (Type driverType, Type mainLoopDriverType)
  210. {
  211. var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  212. var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  213. var mainLoop = new MainLoop (mainLoopDriver);
  214. mainLoop.AddIdle (() => false);
  215. bool result = mainLoop.CheckTimersAndIdleHandlers (out int waitTimeout);
  216. Assert.True (result);
  217. Assert.Equal (-1, waitTimeout);
  218. mainLoop.Dispose ();
  219. }
  220. //[Theory]
  221. //[InlineData (typeof (FakeDriver), typeof (FakeMainLoop))]
  222. //[InlineData (typeof (NetDriver), typeof (NetMainLoop))]
  223. //[InlineData (typeof (CursesDriver), typeof (UnixMainLoop))]
  224. //[InlineData (typeof (WindowsDriver), typeof (WindowsMainLoop))]
  225. //public void MainLoop_Invoke_ValidAction_RunsAction (Type driverType, Type mainLoopDriverType)
  226. //{
  227. // var driver = (ConsoleDriver)Activator.CreateInstance (driverType);
  228. // var mainLoopDriver = (IMainLoopDriver)Activator.CreateInstance (mainLoopDriverType, new object [] { driver });
  229. // var mainLoop = new MainLoop (mainLoopDriver);
  230. // var actionInvoked = false;
  231. // mainLoop.Invoke (() => { actionInvoked = true; });
  232. // mainLoop.RunIteration (); // Run an iteration to process the action.
  233. // Assert.True (actionInvoked);
  234. // mainLoop.Dispose ();
  235. //}
  236. }