cover image
< Inicio
Miscelánea

Cómo convertir automáticamente COBOL a Go

Aunque COBOL puede considerarse un lenguaje heredado, todavía hay miles de millones de líneas de COBOL en producción. Modernizar estos sistemas, que son costosos de ejecutar y mantener, es todo un reto. Una solución a este problema es un transpilador de COBOL a Go que quiero presentar en este artículo.

COBOL

COBOL apareció por primera vez en 1959 y es un lenguaje compilado diseñado para uso empresarial. Hoy en día, principalmente las grandes instituciones financieras y las agencias gubernamentales tienen sistemas que ejecutan COBOL en producción. Se utiliza a menudo en ordenadores centrales, por ejemplo el Z Mainframe con z/OS de IBM. Se trata de un mercado considerable, ya que aproximadamente 10.000 ordenadores mainframe operan en todo el mundo. Aunque las características orientadas a objetos están ahora también disponibles, COBOL es principalmente un lenguaje procedimental e imperativo. Este es un simple programa de la palabra hola en COBOL:

hello.cob

* Sample COBOL program
IDENTIFICATION DIVISION.
PROGRAM-ID. hello.
PROCEDURE DIVISION.
     DISPLAY "Hello, world!".
     STOP RUN.

Usted puede probarlo en su propio ordenador, por ejemplo con GnuCOBOL ejecutando el siguiente comando de compilación:

$ cobc -x hello.cob
$ ./hello

Go

Go es un lenguaje de programación de alto nivel compilado y tipado estáticamente diseñado en Google por Robert Griesemer, Rob Pike y Ken Thompson. Sus ventajas son la baja barrera de entrada para nuevos desarrolladores y que es un lenguaje compilado de rápida ejecución, por lo que es una buena opción cuando se trata de modernizar aplicaciones COBOL heredadas.

El código fuente de Go es fácil de entender, incluso para los programadores nuevos en Go. Esto es una ventaja porque el mercado de desarrolladores de software COBOL es un reto, como describo en la siguiente sección.

Mercado de programadores COBOL

Muchas grandes empresas que tienen sistemas en ejecución en COBOL luchan por atraer a programadores que puedan mantener estos sistemas. La edad media de los programadores de software COBOL es alta y hay pocos programadores jóvenes que quieran aprender COBOL, lo que supone un riesgo para las empresas que tienen muchos miles de millones de líneas de COBOL en producción. Por eso resulta útil una posible solución de migración como COBOL-to-Go de Enno Richter.

Convertidor COBOL-to-Go

El programador senior de COBOL Enno Richter con muchas décadas (50 años) de experiencia en programación COBOL desarrolló un transpilador de COBOL a Go llamado COBOL-to-Go. El transpilador evolucionó a partir de un antiguo proyecto de RPG a COBOL. Soporta el estándar COBOL-85, pero se pueden añadir características de los estándares COBOL más recientes bajo demanda.

Una de sus ventajas es que el código Go resultante es fácil de leer y está claramente estructurado. No es necesario un sistema de ejecución, por lo que el código Go resultante es independiente del sistema COBOL-to-Go. Go compila a muchos sistemas operativos y por lo tanto el programa COBOL se puede ejecutar en potencialmente muchos sistemas operativos.

Todos los derechos del código Go resultante permanecen con los titulares de derechos de autor de código COBOL. Hay transpiladores COBOL alternativos, como un transpilador COBOL a Java en el mercado, pero Enno Richter afirma que los resultados de su transpilador Go son más fáciles de entender y mantener.

Código de ejemplo

El siguiente fragmento muestra el código COBOL en el lado izquierdo y el código Go transpilado resultante en el lado derecho. Puede que necesite desplazarse horizontalmente para ver el código Go resultante:

*                                                                      :00190:  // 00190:      *                                                                                                                                                                                
    *----------------------------------------------------------------*     :00191:  // 00191:      *----------------------------------------------------------------                                                                                                                
    **------* *-----------------------------------------------------**     :00192:  // 00192:      **------* *-----------------------------------------------------*                                                                                                                
    **  30  * *                     P R O G R A M M A B L A U F     **     :00193:  // 00193:      **  30  * *                     P R O G R A M M A B L A U F     *                                                                                                                
    **------* *-----------------------------------------------------**     :00194:  // 00194:      **------* *-----------------------------------------------------*                                                                                                                
     PROCEDURE DIVISION.                                                   :00195:  
    **---------------------------------------------------------------*     :00196:  // 00196:      **---------------------------------------------------------------                                                                                                                
    **  V e r a r b e i t u n g                                      *     :00197:  // 00197:      **  V e r a r b e i t u n g                                                                                                                                                      
    **---------------------------------------------------------------*     :00198:  // 00198:      **---------------------------------------------------------------                                                                                                                
         DISPLAY "Test_02400_START --------".                              :00199:  erse.DISlx(&DIS, "Test_02400_START --------") // COBZEI:00199      
                                                                                    ersestr1 = erse.DISout(fDISPLAY, &DIS, " ") // COBZEI:00199      
    *                                                                      :00200:  // 00200:      *                                                                                                                                                                                
    *                                                                      :00201:  // 00201:      *                                                                                                                                                                                
    **-----------------------------------------------------------*         :00202:  // 00202:      **-----------------------------------------------------------*                                                                                                                   
    **  IF  LITERAL --- NUMERISCH  (Struktur)                    *         :00203:  // 00203:      **  IF  LITERAL --- NUMERISCH  (Struktur)                    *                                                                                                                   
    **-----------------------------------------------------------*         :00204:  // 00204:      **-----------------------------------------------------------*                                                                                                                   
    *    IF 12 > BBB-8                                                     :00205:  // 00205:      *    IF 12 > BBB-8                                                                                                                                                               
    *       MOVE SPACE TO BBB-1                                            :00206:  // 00206:      *       MOVE SPACE TO BBB-1                                                                                                                                                      
    *    END-IF.                                                           :00207:  // 00207:      *    END-IF.                                                                                                                                                                     
    *                                                                      :00208:  // 00208:      *                                                                                                                                                                                
    *                                                                      :00209:  // 00209:      *                                                                                                                                                                                
    **-----------------------------------------------------------*         :00210:  // 00210:      **-----------------------------------------------------------*                                                                                                                   
    **  IF  NUMERISCH  (Struktur) --- LITERAL                    *         :00211:  // 00211:      **  IF  NUMERISCH  (Struktur) --- LITERAL                    *                                                                                                                   
    **-----------------------------------------------------------*         :00212:  // 00212:      **-----------------------------------------------------------*                                                                                                                   
    *    IF BBB-8 > 12                                                     :00213:  // 00213:      *    IF BBB-8 > 12                                                                                                                                                               
    *       MOVE SPACE TO BBB-1                                            :00214:  // 00214:      *       MOVE SPACE TO BBB-1                                                                                                                                                      
    *    END-IF.                                                           :00215:  // 00215:      *    END-IF.                                                                                                                                                                     
    *                                                                      :00216:  // 00216:      *                                                                                                                                                                                
    *                                                                      :00217:  // 00217:      *                                                                                                                                                                                
    **-----------------------------------------------------------*         :00218:  // 00218:      **-----------------------------------------------------------*                                                                                                                   
    **  IF LITERAL --- NUMERISCH  (Nativ)                        *         :00219:  // 00219:      **  IF LITERAL --- NUMERISCH  (Nativ)                        *                                                                                                                   
    **-----------------------------------------------------------*         :00220:  // 00220:      **-----------------------------------------------------------*                                                                                                                   
    *    IF 12 > Z3                                                        :00221:  // 00221:      *    IF 12 > Z3                                                                                                                                                                  
    *       MOVE SPACE TO BBB-1                                            :00222:  // 00222:      *       MOVE SPACE TO BBB-1                                                                                                                                                      
    *    END-IF.                                                           :00223:  // 00223:      *    END-IF.                                                                                                                                                                     
    *                                                                      :00224:  // 00224:      *                                                                                                                                                                                
    *                                                                      :00225:  // 00225:      *                                                                                                                                                                                
    **-----------------------------------------------------------*         :00226:  // 00226:      **-----------------------------------------------------------*                                                                                                                   
    **  IF NUMERISCH (Nativ) --- LITERAL                         *         :00227:  // 00227:      **  IF NUMERISCH (Nativ) --- LITERAL                         *                                                                                                                   
    **-----------------------------------------------------------*         :00228:  // 00228:      **-----------------------------------------------------------*                                                                                                                   
    *    IF Z3 > 12                                                        :00229:  // 00229:      *    IF Z3 > 12                                                                                                                                                                  
    *       MOVE SPACE TO BBB-1                                            :00230:  // 00230:      *       MOVE SPACE TO BBB-1                                                                                                                                                      
    *    END-IF.                                                           :00231:  // 00231:      *    END-IF.                                                                                                                                                                     
    *                                                                      :00232:  // 00232:      *                                                                                                                                                                                
    *                                                                      :00233:  // 00233:      *                                                                                                                                                                                
    **-----------------------------------------------------------*         :00234:  // 00234:      **-----------------------------------------------------------*                                                                                                                   
    **  IF  NUMERISCH (Struktur) ---- NUMERISCH  (Struktur)      *         :00235:  // 00235:      **  IF  NUMERISCH (Struktur) ---- NUMERISCH  (Struktur)      *                                                                                                                   
    **-----------------------------------------------------------*         :00236:  // 00236:      **-----------------------------------------------------------*                                                                                                                   
         IF BBB_8 > HHH                                                    :00237:  if erse.IFNCVCV(&BBB_8_cv, ">", &HHH_cv) {      
            MOVE SPACE TO BBB_1                                            :00238:  erse.MVACVLI(&BBB_1_cv,"SPACE") // COBZEI:00238      
         END-IF.                                                           :00239:  }   // ENDIF      
    *                                                                      :00240:  // 00240:      *                                                                                                                                                                                
    *                                                                      :00241:  // 00241:      *                                                                                                                                                                                
    **-----------------------------------------------------------*         :00242:  // 00242:      **-----------------------------------------------------------*                                                                                                                   
    **  P R O G R A M M - E N D E                                *         :00243:  // 00243:      **  P R O G R A M M - E N D E                                *                                                                                                                   
    **-----------------------------------------------------------*         :00244:  // 00244:      **-----------------------------------------------------------*                                                                                                                   
         DISPLAY "Test_02400 ENDE  -------------".                         :00245:  erse.DISlx(&DIS, "Test_02400 ENDE  -------------") // COBZEI:00245      
                                                                                    ersestr1 = erse.DISout(fDISPLAY, &DIS, " ") // COBZEI:00245      
         STOP RUN.                                                         :00246:  //---------------------------------------------------------------      
                                                                                    //  STOP-RUN  (Ende der  Programmlogik)      
                                                                                    //---------------------------------------------------------------      
                                                                                    os.Exit(0)      
    **--------------------------------------------------------------**     :00247:  // 00247:      **--------------------------------------------------------------*                                                                                                                
    ** Ende :                                                       **     :00248:  // 00248:      ** Ende :                                                       *                                                                                                                
    ** ~~Projekt~111COBOL~Sourcen~Test_02400.cbl       (2023-04-20  **     :00249:  // 00249:      ** //Projekt/111COBOL/Sourcen/Test_02400.cbl       (2023-04-20  *                                                                                                                
    *                                                               **     :00250:  // 00250:      *                                                               *                                                                                                                
    **--------------------------------------------------------------**     :00251:  // 00251:      **--------------------------------------------------------------*     

Como puedes ver, el código Go resultante es fácil de entender y de mantener. Enno Richter está buscando empresas colaboradoras que puedan distribuir su valioso proyecto. Si estás interesado, escríbeme un mensaje o contacta directamente con Enno Richter.

Conclusión

Con este artículo espero que hayas podido ver que existen soluciones al problema de la falta de programadores COBOL en el mercado. Una de estas soluciones es el transpilador COBOL-to-Go que podría ser la pieza que falta de su migración COBOL.

Referencias

Foto de portada por Pete Linforth de Pixabay

Publicado el

25 jul. 2024


Creative Commons License

Este trabajo está licenciado bajo una Creative Commons Attribution 4.0 International License.
Thomas Derflinger

Escrito por Thomas Derflinger

Soy un empresario visionario y desarrollador de software. En este blog escribo principalmente sobre programación web y temas relacionados como el IoT.