Saltar al contenido

Uso de funciones de C# 6 con CodeDomProvider (Roslyn)

Verificamos de forma completamente cada escrito de nuestro sitio web con la meta de mostrarte en todo momento la información con la mayor veracidad y actual.

Actualización: marzo de 2018

Advertencia: NuGet versión 1.0.6 … 1.0.8 no copiará la carpeta /roslyn en el directorio de salida de compilación en proyectos que no sean web. Mejor palo con 1.0.5 https://github.com/aspnet/RoslynCodeDomProvider/issues/38

La compilación en tiempo de ejecución con funciones de C#6 requiere un nuevo compilador, como mencionó @thomas-levesque. Este compilador se puede instalar usando el paquete nuget Microsoft.CodeDom.Providers.DotNetCompilerPlatform.

Para las aplicaciones de escritorio, hay un problema. El equipo de ASP.NET, en su infinita sabiduría, ha codificado la ruta al compilador como binroslyncsc.exe Ver discusión en https://github.com/dotnet/roslyn/issues/9483

Si su aplicación de escritorio está compilada para myappapp.exe, el compilador roslyn estará ubicado en myapproslyncsc.exe, PERO EL CSharpCodeProvider RESOLVERÉ csc.exe como myappbinroslyncsc.exe

Por lo que puedo decir, tienes dos opciones.

  1. Cree una rutina posterior a la construcción y/o instalación que moverá el roslyn subdirectorio a binroslyn.
  2. Arregle el código de tiempo de ejecución a través de la magia negra de reflexión.

Aquí está el #2, al exponer el CSharpCodeProvider como una propiedad en una clase de utilidad.

using System.Reflection;
using Microsoft.CodeDom.Providers.DotNetCompilerPlatform;

static Lazy CodeProvider  get;  = new Lazy(() =>  BindingFlags.NonPublic);

    path.SetValue(settings, ((string)path.GetValue(settings)).Replace(@"binroslyn", @"roslyn"));

    return csc;
);

El proveedor de CodeDOM integrado no es compatible con C# 6. Utilice este en su lugar:

https://www.nuget.org/packages/Microsoft.CodeDom.Providers.DotNetCompilerPlatform/

Se basa en Roslyn y es compatible con las características de C# 6.

Solo cambia esta línea:

CodeDomProvider objCodeCompiler = CodeDomProvider.CreateProvider( "CSharp" );

a esto:

CodeDomProvider objCodeCompiler = new Microsoft.CodeDom.Providers.DotNetCompilerPlatform.CSharpCodeProvider();

Me encontré con este problema recientemente. Por contexto, estaba tratando de ejecutar un proyecto MSTest contra un proyecto de biblioteca usando System.CodeDom, pero siempre daba un compilador que implementaba C# 5, tuviera o no Microsoft.Net.Compilers o Microsoft.CodeDom.Providers.DotNetCompilerPlatform paquetes referenciados por el proyecto bajo prueba.

Mi solución para esto fue:

  • Usar paquete Microsoft.CodeDom.Providers.DotNetCompilerPlatform
  • Establecer paquete PrivateAssets a contentfiles;analyzers
  • Pasar opciones de proveedor con CompilerDirectoryPath establecer en el directorio copiado

El valor predeterminado para PrivateAssets es contentfiles;analyzers;build, por lo que hacer que los proyectos de referencia también copien la carpeta requiere eliminar build del ajuste.

Código de ejemplo:

var compiler = CodeDomProvider.CreateProvider("cs", new Dictionary 
     "CompilerDirectoryPath", Path.Combine(Environment.CurrentDirectory, "roslyn") 
);

Hacer que esto funcione con Microsoft.Net.Compilers sería un poco más tedioso ya que no se hace ninguna copia, pero el paso final de señalar CompilerDirectoryPath en la carpeta de herramientas del paquete es lo mismo.

Comentarios y valoraciones

Si estás contento con lo expuesto, eres capaz de dejar un tutorial acerca de qué le añadirías a este ensayo.

¡Haz clic para puntuar esta entrada!
(Votos: 2 Promedio: 5)


Tags :

Utiliza Nuestro Buscador

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *