Compartir a través de


Invocación de la transformación de texto en una extensión de Visual Studio

Si va a escribir una extensión de Visual Studio, como un comando de menú o un lenguaje específico del dominio, puede usar el servicio de plantillas de texto para transformar plantillas de texto. Obtenga el servicio STextTemplating y lo convierta en ITextTemplating.

Consigue el servicio de plantillas de texto

using Microsoft.VisualStudio.TextTemplating;
using Microsoft.VisualStudio.TextTemplating.VSHost;
...
// Get a service provider - how you do this depends on the context:
IServiceProvider serviceProvider = ...; // An instance of EnvDTE, for example

// Get the text template service:
ITextTemplating t4 = serviceProvider.GetService(typeof(STextTemplating)) as ITextTemplating;

// Process a text template:
string result = t4.ProcessTemplate(filePath, System.IO.File.ReadAllText(filePath));

Pasar parámetros a la plantilla

Puede pasar parámetros a la plantilla. Dentro de la plantilla, puede obtener los valores de parámetro mediante la <#@parameter#> directiva .

Para definir el tipo de un parámetro, debe usar un tipo que sea serializable o que pueda ser convertido para su transferencia. Es decir, el tipo debe declararse con SerializableAttributeo debe derivarse de MarshalByRefObject. Esta restricción es necesaria porque la plantilla de texto se ejecuta en un appDomain independiente. Todos los tipos integrados, como System.String y System.Int32 , son serializables.

Para pasar valores de parámetro, el código de llamada puede colocar valores en el diccionario Session, o en CallContext.

En el ejemplo siguiente se usan ambos métodos para transformar una plantilla de prueba corta:

using Microsoft.VisualStudio.TextTemplating;
using Microsoft.VisualStudio.TextTemplating.VSHost;
...
// Get a service provider - how you do this depends on the context:
IServiceProvider serviceProvider = dte;

// Get the text template service:
ITextTemplating t4 = serviceProvider.GetService(typeof(STextTemplating)) as ITextTemplating;
ITextTemplatingSessionHost sessionHost = t4 as ITextTemplatingSessionHost;

// Create a Session in which to pass parameters:
sessionHost.Session = sessionHost.CreateSession();
sessionHost.Session["parameter1"] = "Hello";
sessionHost.Session["parameter2"] = DateTime.Now;

// Pass another value in CallContext:
System.Runtime.Remoting.Messaging.CallContext.LogicalSetData("parameter3", 42);

// Process a text template:
string result = t4.ProcessTemplate("",
   // This is the test template:
   "<#@parameter type=\"System.String\" name=\"parameter1\"#>"
 + "<#@parameter type=\"System.DateTime\" name=\"parameter2\"#>"
 + "<#@parameter type=\"System.Int32\" name=\"parameter3\"#>"
 + "Test: <#=parameter1#>    <#=parameter2#>    <#=parameter3#>");

// This test code yields a result similar to the following line:
//     Test: Hello    07/06/2010 12:37:45    42

Informes de errores y la directiva de salida

Los errores que surjan durante el procesamiento se mostrarán en la ventana de error de Visual Studio. Además, puede recibir una notificación de errores especificando un callback que implemente ITextTemplatingCallback.

Si desea escribir la cadena de resultado en un archivo, es posible que quiera saber qué extensión de archivo y codificación se han especificado en la <#@output#> directiva de la plantilla. Esta información también se pasará al callback. Para obtener más información, vea Directiva de salida T4.

void ProcessMyTemplate(string MyTemplateFile)
{
  string templateContent = File.ReadAllText(MyTemplateFile);
  T4Callback cb = new T4Callback();
  // Process a text template:
  string result = t4.ProcessTemplate(MyTemplateFile, templateContent, cb);
  // If there was an output directive in the MyTemplateFile,
  // then cb.SetFileExtension() will have been called.
  // Determine the output file name:
  string resultFileName =
    Path.Combine(Path.GetDirectoryName(MyTemplateFile),
        Path.GetFileNameWithoutExtension(MyTemplateFile))
      + cb.fileExtension;
  // Write the processed output to file:
  File.WriteAllText(resultFileName, result, cb.outputEncoding);
  // Append any error messages:
  if (cb.errorMessages.Count > 0)
  {
    File.AppendAllLines(resultFileName, cb.errorMessages);
  }
}

class T4Callback : ITextTemplatingCallback
{
  public List<string> errorMessages = new List<string>();
  public string fileExtension = ".txt";
  public Encoding outputEncoding = Encoding.UTF8;

  public void ErrorCallback(bool warning, string message, int line, int column)
  { errorMessages.Add(message); }

  public void SetFileExtension(string extension)
  { fileExtension = extension; }

  public void SetOutputEncoding(Encoding encoding, bool fromOutputDirective)
  { outputEncoding = encoding; }
}

El código se puede probar con un archivo de plantilla similar al siguiente:

<#@output extension=".htm" encoding="ASCII"#>
<# int unused;  // Compiler warning "unused variable"
#>
Sample text.

La advertencia del compilador aparecerá en la ventana de error de Visual Studio y también generará una llamada a ErrorCallback.

Parámetros de referencia

Puede pasar valores de una plantilla de texto mediante una clase de parámetros derivada de MarshalByRefObject.

Para generar texto a partir de una plantilla de texto preprocesada: llame al TransformText() método de la clase generada. Para obtener más información, consulte Generación de texto en tiempo de ejecución con plantillas de texto T4.

Para generar texto fuera de una extensión de Visual Studio: defina un host personalizado. Para obtener más información, consulte Procesamiento de plantillas de texto mediante un host personalizado.

Para generar código fuente que se pueda compilar y ejecutar más adelante: llame al método PreprocessTemplate de ITextTemplating.