2011-04-16 16 views
5

Tengo una biblioteca existente escrita en C# que envuelve una API de TCP/IP de nivel mucho más bajo y expone los mensajes que vienen del servidor desde un servidor (protocolo binario patentado) como eventos .NET. También proporciono llamadas de método sobre un objeto que maneja las complejidades de ordenar tipos .NET convenientes (como System.DateTime) hasta las codificaciones binarias y las estructuras de longitud fija que requiere la API (para los mensajes salientes al servidor). Existe un buen número de aplicaciones existentes (tanto internamente como utilizadas por terceros) creadas sobre esta biblioteca .NET.¿Alguna mejor opción que transferir desde C# a Java?

Recientemente, alguien que no quiere hacer todo el trabajo de abstracción del TCP/IP, nos ha abordado, pero su entorno no es estrictamente Windows (supongo * nix, pero no estoy 100% seguro), y han insinuado que su ideal sería algo invocable de Java.

¿Cuál es la mejor manera de mantener a sus necesidades, sin tener que:

  1. Puerto del código de Java ahora (incluyendo un archivo DLL no administrado que actualmente P/Invoke en la descompresión)
  2. Tener a mantener dos bases de código separadas yendo hacia adelante (es decir, hacer las mismas correcciones de errores y mejoras de características dos veces)

Una cosa que he considerado es volver a escribir la mayor parte de la funcionalidad central de TCP/IP en algo más multiplataforma (C/C++) y el n cambiar mi biblioteca .NET para que sea una capa delgada encima de esto (¿P/Invocar?), y luego también escribir una capa Java delgada similar sobre la misma (¿JNI?).

Pros:

  • Yo sobre todo pasar mi tiempo escribiendo cosas sólo una vez.

Contras:

  • mayor parte del código no administrado sería ahora - no es el fin del mundo, pero no es ideal desde el punto de vista de la productividad (para mí).
  • más largo tiempo de desarrollo (no puede puerto de código C# sockets en C/C++ tan pronto como se acaba de migración a Java) [¿Qué tan cierto es esto?]
  • En este punto, la API subyacente es sobre todo envuelto y la biblioteca es muy estable, por lo que probablemente no haya muchos desarrollos nuevos; puede que no sea tan malo simplemente transferir el código actual a Java y luego tener que corregir errores ocasionalmente o exponer nuevos campos dos veces en el futuro.
  • Posible inestabilidad para mis aplicaciones cliente existentes mientras la versión en la que se ejecutan cambia drásticamente debajo de ellas. (Por encima de mi cabeza puedo pensar en problemas de 32/64 bits, problemas de endianness y errores generales que pueden surgir durante el puerto, etc.)

Otra opción que he considerado brevemente es de alguna manera manipular Mono hasta Java, para que pueda aprovechar todo el código C existente que ya tengo. Sin embargo, no estoy muy al tanto de cuán suave será la experiencia del desarrollador para los desarrolladores de Java que la tengan que consumir. Estoy bastante seguro de que la mayor parte del código debería ejecutarse sin problemas bajo Mono (bar la P/Invoke de descompresión que de todos modos debería portarse a C#).

Lo ideal sería que no quisiera agregar otra capa de TCP/IP, tuberías, etc. entre mi código y la aplicación cliente de Java si puedo ayudarlo (así que WCF a Java-side WS-DeathStar probablemente esté fuera) .Nunca he hecho ningún desarrollo serio con Java, pero me enorgullece el hecho de que la biblioteca es actualmente un pedazo de pastel para que un desarrollador externo se integre en su aplicación (siempre y cuando ejecute .NET por supuesto:)), y me gustaría poder mantener la misma facilidad de uso para cualquier desarrollador de Java que quiera la misma experiencia.

Así que si alguien tiene opiniones sobre las 3 opciones que he propuesto (puerto a Java & mantener dos veces, portar a C y escribir enlaces delgados para .NET y Java o, intente e integrar Java y Mono), o cualquier otras sugerencias Me encantaría escucharlos.

Gracias

Editar: Después de hablar directamente con el desarrollador en el cliente (es decir, la eliminación del teléfono roto También conocido como departamento de ventas) los requisitos han cambiado lo suficiente que esta cuestión ya no se aplica muy bien a mi situación inmediata. Sin embargo, dejaré la pregunta abierta con la esperanza de que podamos generar algunas más buenas sugerencias.

En mi caso particular, el cliente realmente ejecuta máquinas con Windows además de Solaris (¿quién no en estos días?) Y está feliz de que podamos escribir una aplicación (Servicio de Windows) en la parte superior de la biblioteca y proporcionar API TCP/IP más simple y más pequeña para que puedan codificar. Traduciremos sus mensajes simples en el formato que entiende el sistema downstream, y traduciremos las respuestas recibidas para que puedan consumir, de modo que puedan continuar interactuando con este sistema downstream a través de su aplicación Java.

Volviendo al escenario original después de pensar en esto por un par de semanas, yo tengo unas cuantas más comentarios:

  • Una biblioteca portátil basado en C con diferentes enlaces de lenguaje en la parte superior sería probablemente el camino a seguir si sabías desde el principio que necesitarías soportar múltiples idiomas/plataformas.

  • En * nix, puede un solo host proceso tanto un tiempo de ejecución de Java y un tiempo de ejecución Mono al mismo tiempo? Sé que en versiones anteriores de .NET no podía tener dos tiempos de ejecución de .NET diferentes en el mismo proceso, pero creo que lo arreglaron con .NET 4. Si esto es posible, ¿cómo se podría comunicar uno entre los dos? Idealmente, desearía algo tan simple como una llamada a un método estático y un delegado para generar respuestas.

  • Si no hay soporte para la interfaz directa entre Java fácil & Mono (métodos & delegados, etc.), se podría considerar el uso de algo así como ZeroMQ con Protocol Buffers o Apache Thrift como el formato de mensaje. Esto funcionaría en proceso, entre procesos y en la red debido al soporte de ZeroMQ para diferentes transportes.

Respuesta

2

Dedique más tiempo a determinar los requisitos antes de decidirse por una implementación. Hasta que sepa lo que se requiere, no tiene ningún criterio para elegir entre diseños.

Si se trata de un entorno que no sea Windows, no tiene sentido tener .NET en cualquier lugar allí, por ejemplo.

+0

He marcado su respuesta como correcta, porque mis requisitos terminaron cambiando. Sin embargo, no estoy muy satisfecho con esto, aún puede haber escenarios en los que se requiera este tipo de interoperabilidad después de un exhaustivo análisis de requisitos, por lo que aún espero que se presente una mejor respuesta. –

+0

la respuesta corta: no, no creo que haya mejores opciones que la portación de C# a Java :) pero esa puede no ser una solución adecuada dado lo que el cliente necesita para el código, cuánto está dispuesto a pagar, etc. . –

1

¿Ha considerado mono? Lo más probable es que admita su código existente en el entorno que no sea Windows. El truco sería llamarlo desde Java, pero los mononucleos pueden tener algo para ayudarte también.

1

Esto probablemente no es la solución más adecuada en su caso, pero está completo:

Hay algunos idiomas que pueden dirigirse tanto a la JVM y.NET, en particular Ruby (JRuby y IronRuby) y Python (Jython y IronPython). Scala eventualmente podría llegar allí, aunque ahora mismo la versión de .NET está muy por detrás de la versión de JVM.

De todos modos, podría reescribir su biblioteca en Ruby o Python y enfocarse en ambos tiempos de ejecución.

0

Una cosa que he considerado es volver a escribir la mayor parte de la funcionalidad core TCP/IP una vez en algo más multiplataforma (C/C++) y luego cambiar mi biblioteca .NET para que sea una capa delgada en al principio de esto (¿P/Invocar?), y luego escriba también una capa de Java similarmente fina encima (¿JNI?).

Esa es una posibilidad. En el lado de Java, debería considerar usar JNA en lugar de JNI. (Si usa JNI, el código C/C++ debe escribirse para usar firmas específicas de JNI.)

Otra posibilidad es reemplazar el protocolo binario patentado por algo que "simplemente funciona" con múltiples lenguajes de programación. Este es el tipo de espacio problemático donde CORBA y tecnologías similares proporcionan una buena solución.

2

Si necesita algo que se ejecute en la máquina virtual de Java pero se parece mucho a C#, debe consultar Stab. Esto no lo ayudará con P/Invoke y similares, pero puede que le cueste menos portar su código C# a Java y mantenerlo.

Sin embargo, debe consultar Mono. Espero que todo su código C# se ejecute sin modificaciones (excepto las partes que tocan la DLL no administrada).

No lo he usado pero jni4net se supone que permite llamar al código .NET de Java. Si sus clientes desean una interfaz Java, esta puede ser una solución.

Utilizo Mono en Linux y Mac todo el tiempo, incluso cuando la compatibilidad con .NET no es una prioridad. Me gustan las bibliotecas C# y .NET y prefiero la CLR a la JVM. Mono tiene licencia MIT/X11, lo que significa que puede usarlo comercialmente si lo desea. A diferencia de otros, no veo ninguna razón para evitar la tecnología promovida por Microsoft y favorecer la tecnología defendida por Oracle e IBM.

El uso de Mono no lo ayudará con los bits no administrados, aunque puede P/Invocar en una DLL nativa. Simplemente deberá portar esa DLL usted mismo o buscar algún equivalente.

Es posible que también desee buscar en Mono Ahead of Time compilation.

1

Si lo que realmente quiere es poder codificar en .NET y ejecutarlo en la JVM, podría check out Grasshopper (2015-09: enlace posiblemente muerto). Eso es lo que está diseñado para hacer.

Sé que los chicos de Mainsoft han contribuido al Mono en los últimos años. Si no recuerdo mal, escribieron el compilador de Visual Basic para Mono.

También está el C# to Java converter from Tangible. He oído cosas buenas pero nunca las he usado.

Además, no ayuda mucho a su situación, pero debo señalar Mono for Android.

Mono para Android ejecuta el CLR y el Dalvik VM en paralelo. En otras palabras, el código de C# que escribió para Android puede llamar a las bibliotecas de Java (como la interfaz de usuario de Android, por ejemplo) y ejecutarlo como una aplicación única. Usted había preguntado sobre la posibilidad de ejecutar el código .NET y Java en el mismo proceso.Claramente, se puede hacer.

Cuestiones relacionadas