Come verificare la versione del sistema operativo in fase di esecuzione, ad es. Windows o linux senza usare una dichiarazione di compilazione condizionale

Qualcuno sa come determinare su quale piattaforma è in esecuzione il codice c #, ad esempio se è in esecuzione su linux o windows in modo da poter eseguire codice diverso in fase di runtime.

Ho app # windows che voglio build per il targeting di windows e piattaforms Linux.

Finora ho creato 2 file di progetto che puntavano allo stesso insieme di file di codice sorgente. Quindi utilizzo una dichiarazione di compilazione condizionale uno dei progetti chiamati LINUX.

Dove ci sono delle differenze nel codice reale uso le istruzioni di codifica usando l’istruzione di compilazione condizionale, ad es

#if (LINUX) ' do something #endif 

C’è un modo migliore per farlo? Non voglio davvero avere 2 file di progetto.

Grazie in anticipo.

È ansible rilevare la piattaforma di esecuzione utilizzando System.Environment.OSVersion.Platform :

 public static bool IsLinux { get { int p = (int) Environment.OSVersion.Platform; return (p == 4) || (p == 6) || (p == 128); } } 

Dalle FAQ Mono :

Come rilevare la piattaforma di esecuzione?

La piattaforma di esecuzione può essere rilevata utilizzando il valore System.Environment.OSVersion.Platform . Tuttavia, il rilevamento corretto delle piattaforms Unix, in tutti i casi, richiede un po ‘più di lavoro. Le prime versioni del framework (1.0 e 1.1) non includevano alcun valore PlatformID per Unix, quindi Mono usava il valore 128. Il più recente framework 2.0 aggiungeva Unix all’enum PlatformID ma, purtroppo, con un valore diverso: 4 e più recente versioni di .NET distinte tra Unix e MacOS X, introducendo ancora un altro valore 6 per MacOS X.

Ciò significa che per rilevare correttamente il codice in esecuzione su piattaforms Unix è necessario verificare i tre valori (4, 6 e 128). Ciò garantisce che il codice di rilevamento funzioni come previsto quando viene eseguito su Runtime 1.x Mono CLR e con i runtime Mono e Microsoft CLR 2.x.

Che ne dite di

 System.Environment.OSVersion 

Ho trovato questa raccomandazione su uno dei blog di Microsoft:

Ti consigliamo di utilizzare RuntimeInformation.IsOSPlatform () per i controlli della piattaforma.

Riferimento: https://blogs.msdn.microsoft.com/dotnet/2017/11/16/announcing-the-windows-compatibility-pack-for-net-core/

IsOSPlatform() accetta un argomento di tipi OSPlatform che ha 3 valori per impostazione predefinita: Windows , Linux e OSX . Può essere usato come segue:

 if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { // Do something } 

L’API fa parte di .NET Standard 2.0 e pertanto è disponibile in .NET Core 2.0 e .NET Framework 4.7.1.

È ansible utilizzare System.Environment.OSVersion per verificare il tipo di piattaforma su cui ci si trova in fase di runtime.

Per espandere altre risposte, nei casi in cui un’implementazione di una funzionalità di Linux e Windows non è compatibile (es .: richiedi riferimenti a librerie disponibili solo per una piattaforma specifica), puoi anche usare un’interfaccia e avere due assembly separati, uno scritto e compilato su ogni piattaforma, con un tipo che implementa questa interfaccia. Quindi, in base al controllo, utilizzare Assembly.Load () per caricare solo l’assembly corretto (ed è la dipendenza specifica della piattaforma), il reflection per trovare il proprio tipo nell’assembly e Activator.CreateInstance () per ottenere un’istanza del tipo che puoi quindi lavorare normalmente.