Colabora
 

Uso de .NET como objeto COM

Convertidor de RTF a Texto

 

Fecha: 30/Abr/2009 (24-04-09)
Autor: Antonio R. Barbado Portillo - antoniobarbado at gmail dot com

 


Introducción

Todo comenzó cuando diseñé una plataforma web en PHP para trabajar con una aplicación existente. El problema que me encontré era que algunos campos en la base de datos traían texto en formato RTF porque la aplicación los cargaba en un RichTextBox para mostrarlo en su aplicación Windows Forms.

El caso es que cuando accedía estos campos y los cargaba en un textarea html me mostraba la codificación rtf {\rtf1\par etc.. mezclado con el texto que contenia dicho campo con lo que necesitaba parsear ese rtf a texto para que los usuarios vieran una version de texto sin formato.

Si usas PHP en servidores windows, existe la posibilidad de usar objetos COM. Actualmente .NET tiene la capacidad de poder generar interoperabilidad COM en las DLL (Librerias de clases) que se generan con Visual Studio. En realidad lo que genera no es una DLL COM "nativa" que se pueda registrar con el comando regsvr32 como otras, sino que gracias a un wrapper COM de .NET expone este ensamblado (DLL) como si de un objecto COM se tratara.

Para ello, me pasé horas buscando información por internet y al final decidí crearme mi propio convertidor usando la propia librería de clases de .NET

Paso 1. Creamos nuestra DLL.

Lo primero fué crearme mi DLL, para ello cree un nuevo proyecto de libreria de clases. Elimine la clase que te genera por defecto y añadí un nuevo elemento llamado Clase COM (COM class).

Una vez hecho esto, el propio Visual Studio te genera los identificadores necesarios para que tu clase sea un clase COM válida, p.e que tenga un constructor sin parametros para que servidor lo pueda instanciar y sus identificadores necesarios.

Ya solo nos falta añadir la funcionalidad deseada a nuestra dll, en mi caso que nos convierta rtf a txt usando como "convertidor" el richtextbox.  Aquí pego el código

<ComClass(Rtf2txt.ClassId, Rtf2txt.InterfaceId, Rtf2txt.EventsId)> _
Public Class Rtf2txt

#Region "GUID de COM"
    ' Estos GUID proporcionan la identidad de COM para esta clase 
    ' y las interfaces de COM. Si las cambia, los clientes 
    ' existentes no podrán obtener acceso a la clase.
    Public Const ClassId As String = "6bb5e369-448b-45e1-a157-a754d6232484"
    Public Const InterfaceId As String = "cf05e0fc-28c4-4a16-a355-a772d21bfd81"
    Public Const EventsId As String = "05502bdc-5212-485c-b566-16a35ed40e2f"
#End Region

    ' Una clase COM que se puede crear debe tener Public Sub New() 
    ' sin parámetros, si no la clase no se 
    ' registrará en el registro COM y no se podrá crear a 
    ' través de CreateObject.
    Public Sub New()
        MyBase.New()
    End Sub

    Public Function Convertir(ByVal strCampoRtf As String) As String

        Dim c As New System.Windows.Forms.RichTextBox()
        Dim s As String = String.Empty

        If Not String.IsNullOrEmpty(entrada) Then
            Try
                c.Rtf = strCampoRtf
                s = c.Text
            Catch ex As Exception
                s = strCampoRtf
            End Try
        End If

        Return s

    End Function

End Class

Nota:
Este código necesita que agregueis una referencia al System.Windows.Forms que es la que contiene la clase RitchTextBox

 

Compilación de la librería y registrar interoperabilidad COM

Ahora debemos activar "Registrar para Interoperabilidad COM" en el apartado "Compilar" de las propiedades del proyecto, aunque no estoy muy seguro de que al añadir una clase COM ya Visual Studio lo activa por nosotros.. pero por si acaso, le echamos un vistazo y listo.

Si generamos el proyecto, Visual Studio nos genera la dll y nos la instala en COM automaticamente con lo que si tenemos nuestro servidor web con PHP en la misma máquina podemos usar la interfaz COM de nuestra dll de forma instantánea.

Para ello usariamos, por ejemplo desde PHP

$p = new COM("Convertidor.Rtf2txt");
echo $p->Convertir("PEPE");

Donde Convertidor es el nombre del proyecto y Rtf2txt el nombre de la clase dentro de mi proyecto. Así mismo si posteriormente añadimos mas funciones útiles las usaríamos como Convertidor.<<NOMBRE DE LA CLASE>>

Registro de la DLL en otro servidor

Aquí es donde viene lo bueno y donde mas me dolió la cabeza, ya que aquí tuve que averiguar como hacerlo al no tener el Visual Studio que lo hacía por mí.

En primer lugar, debemos registrar la dll en el equipo que queramos que use dicha librería. Por supuesto, que dicho equipo debe tener el .NET Framework que hayamos usado para generar nuestra dll, en mi caso el 2.0

Para registrar la dll, copiamos la dll de nuestro directorio Release o Debug, y movemos la dll a un sitio en el PATH del equipo y ejecutamos la herramienta regasm (que está disponible en la ruta donde se instala el .Net Framework), usando /tbl para que genere la libreria de tipos y /codebase para que incluya el path seleccionado de la dll ya que no está en la caché de ensamblados.

C:\> C:\Windows\Microsoft.NET\Framework\v2.0.50727\RegAsm.exe C:\php5\Convertidor.dll 
/tlb:C:\Php5 Convertidor.tlb /codebase

Microsoft (R) .NET Framework Assembly Registration Utility 2.0.50727.1433
Copyright (C) Microsoft Corporation 1998-2004.  All rights reserved.

Types registered successfully
Assembly exported to 'C:\Php5\Convertidor.tlb', and the type library was registered successfully

C:\>

Una vez hecho esto, generará un mensaje como este y si es así ya tenemos disponible la dll para usarla desde el servidor Web con PHP y COM.

Nota:
Si probais la dll, y despues quereis sustituirla porque la habeis actualizado, recordad reiniciar el servidor web para que la libere y así podais sobrescribirla, sino os dará error de acceso denegado por archivo en uso.

Para el caso que nos ocupa, tened cuidado con el texto que se le pasa al campo Rtf, sino es código Rtf (osea con sus {\rtf1 etc..}) dará error de formato no válido.

Despues de navegar muchas horas buscando información sobre el tema de registro de COM generadas con .NET en otros equipos, este es el enlace que me dió la respuesta: How to register .NET Assembly for COM Interop ?


Espacios de nombres usados en el código de este artículo:

System.Windows.Forms

 



Compromiso del autor del artículo con el sitio del Guille:

Lo comentado en este artículo está probado (y funciona) con la siguiente configuración:

El autor se compromete personalmente de que lo expuesto en este artículo es cierto y lo ha comprobado usando la configuración indicada anteriormente.

En cualquier caso, el Guille no se responsabiliza del contenido de este artículo.

Si encuentras alguna errata o fallo en algún link (enlace), por favor comunícalo usando este link:

Gracias.


Código de ejemplo (comprimido):

 

Es muy poco codigo para colgarlo

 


Ir al índice principal de el Guille