2009-11-03 5 views
8

Sono interessato a routine/procedure/metodi comuni che potresti utilizzare in Program.cs durante la creazione di un progetto .NET. Ad esempio, utilizzo comunemente il seguente codice nelle mie applicazioni desktop per consentire aggiornamenti semplici, esecuzione di singole istanze e reporting semplice e amichevole degli errori delle applicazioni di sistema non rilevati.Quali routine comuni inserisci in Program.cs per C#


using System; 
    using System.Diagnostics; 
    using System.Threading; 
    using System.Windows.Forms; 

    namespace NameoftheAssembly 
    { 
     internal static class Program 
     { 
      /// <summary> 
      /// The main entry point for the application. Modified to check for another running instance on the same computer and to catch and report any errors not explicitly checked for. 
      /// </summary> 
      [STAThread] 
      private static void Main() 
      { 
       //for upgrading and installing newer versions 
       string[] arguments = Environment.GetCommandLineArgs(); 
       if (arguments.GetUpperBound(0) > 0) 
       { 
        foreach (string argument in arguments) 
        { 
         if (argument.Split('=')[0].ToLower().Equals("/u")) 
         { 
          string guid = argument.Split('=')[1]; 
          string path = Environment.GetFolderPath(Environment.SpecialFolder.System); 
          var si = new ProcessStartInfo(path + "\\msiexec.exe", "/x" + guid); 
          Process.Start(si); 
          Application.Exit(); 
         } 
        } 
        //end of upgrade 
       } 
       else 
       { 
        bool onlyInstance = false; 
        var mutex = new Mutex(true, Application.ProductName, out onlyInstance); 
        if (!onlyInstance) 
        { 
         MessageBox.Show("Another copy of this running"); 
         return; 
        } 
        AppDomain.CurrentDomain.UnhandledException += CurrentDomain_UnhandledException; 
        Application.ThreadException += ApplicationThreadException; 
        Application.EnableVisualStyles(); 
        Application.SetCompatibleTextRenderingDefault(false); 
        Application.Run(new Form1()); 
       } 
      } 

      private static void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e) 
      { 
       try 
       { 
        var ex = (Exception) e.ExceptionObject; 
        MessageBox.Show("Whoops! Please contact the developers with the following" 
            + " information:\n\n" + ex.Message + ex.StackTrace, 
            " Fatal Error", MessageBoxButtons.OK, MessageBoxIcon.Stop); 
       } 
       catch (Exception) 
       { 
        //do nothing - Another Exception! Wow not a good thing. 
       } 
       finally 
       { 
        Application.Exit(); 
       } 
      } 

      public static void ApplicationThreadException(object sender, ThreadExceptionEventArgs e) 
      { 
       try 
       { 
        MessageBox.Show("Whoops! Please contact the developers with the following" 
            + " information:\n\n" + e.Exception.Message + e.Exception.StackTrace, 
            " Error", MessageBoxButtons.OK, MessageBoxIcon.Stop); 
       } 
       catch (Exception) 
       { 
        //do nothing - Another Exception! Wow not a good thing. 
       } 
      } 
     } 
    } 

Trovo queste routine per essere molto utile. Quali metodi hai trovato utili in Program.cs?

+0

Trovo abbastanza orribile il fatto che si stiano lasciando cadere altre eccezioni sul pavimento. –

+3

Non penso che lascerà altre eccezioni sul pavimento. Le uniche eccezioni che egli ignora sono quelle causate quando mostra effettivamente un messaggio di errore all'utente, cioè la chiamata a MessageBox.Show(). –

risposta

5

Cerco di evitare di inserire qualcosa di significativo nel file Program.cs. Qualunque cosa io scriva per una semplice app Console potrebbe un giorno essere spostata in una libreria di classi, e così costruirò una classe separata per la logica del programma reale.

Detto questo, c'è un codice generico che uso più e più volte. La cosa principale è usare la classe Trace per gestire l'output della console, quindi non devo modificare alcun codice importante nell'app stessa per reindirizzare le cose a un file di registro o altrove quando l'inevitabile transizione alla libreria di classi o all'app gui verifica:

using System; 
using System.Diagnostics; 

public static void Main(string[] args) 
{ 
    Trace.Listeners.Add(new ConsoleTraceListener()); 
    Trace.WriteLine("Program Started - " + DateTime.Now.ToString());Trace.WriteLine(""); 

    //Call into a separate class or method for the actual program logic 
    DoSomething(); //I'll use Trace for output in here rather than Console 

    Trace.WriteLine("");Trace.WriteLine("Program Finished - " + DateTime.Now.ToString()); 

    Console.Write("Press a key to exit..."); 
    Console.ReadKey(true); 
    Console.WriteLine(); 
} 
+0

È un'ottima idea! – Rick

1

di solito ho una piccola funzione principale che chiama un'altra funzione (ad esempio Start) - in questo modo, se qualche assemblaggio è mancante e di inizio non può essere JITted, posso prendere il TypeLoadException e visualizzare un uomo- messaggio di errore leggibile.

2

Per l'analisi degli argomenti, la classe Novell Options è la migliore che abbia mai visto (via "Best way to parse command line arguments in C#"). Ho anche adapted it per le applicazioni della console interattiva, per i programmi che non solo eseguono e abbandonano.

Ecco un esempio della classe Opzioni:

static void Main(string[] args) 
{ 
    var p = new new OptionSet() 
     .Add ("v|verbose", v=> setVerbose()) 
     .Add ("h|?|help", v=> showHelp()) 
     .Add ("n|name=", v=> showName(v)); 

    p.Parse (args); 
} 
1

Utilizziamo solitamente principale per riga di comando di base l'analisi, l'installazione di movimentazione incidente, verifica delle licenze, e la creazione di form principale (ammesso che è un'applicazione Windows e non un'applicazione console).

Tuttavia, la maggior parte di tale funzionalità è gestita da altri oggetti che principale appena un'istanza e chiamate.

0

L'unico codice che sicuramente ma in ogni programma è il mio gestore delle eccezioni:

All'inizio:

#If Not Debug Then 
     AddHandler AppDomain.CurrentDomain.UnhandledException, AddressOf Me.Application_UnhandledException 
     AddHandler Application.ThreadException, AddressOf Me.Application_ThreadException 
#End If 

Private Sub Application_UnhandledException(ByVal sender As Object, ByVal e As System.UnhandledExceptionEventArgs) 
    Me.UnhandledExceptionLog(TryCast(e.ExceptionObject, Exception).Message, New StackTrace(TryCast(e.ExceptionObject, Exception), True), e.ExceptionObject) 
End Sub 
Private Sub Application_ThreadException(ByVal sender As Object, ByVal e As System.Threading.ThreadExceptionEventArgs) 
    Me.UnhandledExceptionLog(e.Exception.Source & Environment.NewLine & e.Exception.Message & Environment.NewLine & e.Exception.StackTrace, New StackTrace(e.Exception, True), e.Exception) 
End Sub 

Public Sub UnhandledExceptionLog(ByVal message As String, ByVal stack As StackTrace, ByVal ex As Object) 
    ' write the exception details to a log and inform the user the he screwed something ;) ' 
End Sub 

Questo attirerà ogni Eccezione mi mancava e volontà scriverlo in un log del mio (chiedendo al client quale sia il messaggio di errore dichiarato in realtà non è la cosa più saggia ...).

Bobby

Problemi correlati