55 using System . Threading ;
66 using System . Threading . Tasks ;
77 using Microsoft . AspNetCore . Hosting ;
8+ using Microsoft . Extensions . Configuration ;
9+ using Serilog ;
810 using SqlStreamStore . Streams ;
911
10- internal static class Program
12+ internal class Program : IDisposable
1113 {
1214 private static readonly Random s_random = new Random ( ) ;
13- private const int DefaultPort = 8001 ;
15+ private readonly CancellationTokenSource _cts ;
16+ private readonly InMemoryStreamStore _streamStore ;
17+ private readonly IWebHost _host ;
18+ private readonly IConfigurationRoot _configuration ;
19+
20+ private bool Interactive => _configuration . GetValue < bool > ( "interactive" ) ;
1421
1522 public static async Task < int > Main ( string [ ] args )
1623 {
17- if ( ! int . TryParse ( args . FirstOrDefault ( ) , out var port ) )
24+ Log . Logger = new LoggerConfiguration ( )
25+ . MinimumLevel . Debug ( )
26+ . Enrich . FromLogContext ( )
27+ . WriteTo . Console ( )
28+ . CreateLogger ( ) ;
29+
30+ using ( var program = new Program ( args ) )
1831 {
19- port = DefaultPort ;
32+ return await program . Run ( ) ;
2033 }
34+ }
2135
22- var url = new UriBuilder { Port = port } . Uri . ToString ( ) ;
23-
24- using ( var cts = new CancellationTokenSource ( ) )
25- using ( var streamStore = new InMemoryStreamStore ( ) )
26- using ( var host = new WebHostBuilder ( )
27- . UseUrls ( url )
36+ private Program ( string [ ] args )
37+ {
38+ _cts = new CancellationTokenSource ( ) ;
39+ _streamStore = new InMemoryStreamStore ( ) ;
40+ _host = new WebHostBuilder ( )
2841 . UseKestrel ( )
29- . UseStartup ( new DevServerStartup ( streamStore ) )
30- . Build ( ) )
31- {
42+ . UseStartup ( new DevServerStartup ( _streamStore ) )
43+ . UseSerilog ( )
44+ . Build ( ) ;
45+ _configuration = new ConfigurationBuilder ( )
46+ . AddEnvironmentVariables ( )
47+ . AddCommandLine ( args )
48+ . Build ( ) ;
49+ }
3250
33- var serverTask = host . RunAsync ( cts . Token ) ;
51+ private async Task < int > Run ( )
52+ {
53+ try
54+ {
55+ var serverTask = _host . RunAsync ( _cts . Token ) ;
3456
35- DisplayMenu ( streamStore , url ) ;
57+ if ( Interactive )
58+ {
59+ Log . Warning ( "Running interactively." ) ;
60+ DisplayMenu ( _streamStore ) ;
61+ }
3662
3763 await serverTask ;
38- }
3964
40- return 0 ;
65+ return 0 ;
66+ }
67+ catch ( Exception ex )
68+ {
69+ Log . Fatal ( ex , "Host terminated unexpectedly." ) ;
70+ return 1 ;
71+ }
72+ finally
73+ {
74+ Log . CloseAndFlush ( ) ;
75+ }
4176 }
4277
43- private static void DisplayMenu ( IStreamStore streamStore , string url )
78+ private static void DisplayMenu ( IStreamStore streamStore , string url = null )
4479 {
4580 while ( true )
4681 {
@@ -79,14 +114,14 @@ private static void Write(IStreamStore streamStore, string url, int messageCount
79114
80115 Task . Run ( ( ) => Task . WhenAll (
81116 from streamId in streams
82- select streamStore . AppendToStream ( streamId ,
117+ select streamStore . AppendToStream (
118+ streamId ,
83119 ExpectedVersion . NoStream ,
84120 GenerateMessages ( messageCount ) ) ) ) ;
85121 }
86122
87123 private static NewStreamMessage [ ] GenerateMessages ( int messageCount )
88- {
89- return Enumerable . Range ( 0 , messageCount )
124+ => Enumerable . Range ( 0 , messageCount )
90125 . Select ( _ => new NewStreamMessage (
91126 Guid . NewGuid ( ) ,
92127 "test" ,
@@ -97,6 +132,12 @@ private static NewStreamMessage[] GenerateMessages(int messageCount)
97132 } ] }}",
98133 "{}" ) )
99134 . ToArray ( ) ;
135+
136+ public void Dispose ( )
137+ {
138+ _host ? . Dispose ( ) ;
139+ _streamStore ? . Dispose ( ) ;
140+ _cts ? . Dispose ( ) ;
100141 }
101142 }
102143}
0 commit comments