MokaByte Numero 18 - Aprile 1998

 
Corba & Java
I parte
di 
Olindo Pindaro
Una accoppiata vincente per l'integrazione di sistemi eterogenei 

 


Questo è il primo di una serie di articoli in cui illustreremo la tecnologia CORBA e come essa possa essere usata insieme a Java per integrare sistemi hardware/software eterogenei.



 
 
CORBA: una Architettura per l' Integrazione ed il Riuso.
Negli anni 80 la tecnologia Client-Server sembrava essere l'architettura definitiva per realizzazione dei sistemi informatici, ma essa ha ben presto cominciato a mostrare tutti i suoi limiti: client bisognosi di potenza di elaborazione sempre maggiore, aumento esponenziale della complessita' dei sistemi all' aumentare delle funzioni, difficoltà a cambiare le funzioni senza dovere riprogettare tutto , forte mancanza di metodologie industriali (leggi standard) per progettare i sistemi e soprattutto per integrare applicazioni preesitenti.< 
Nel 1989 per superare tutti i problemi precedendemente elencati è stato creato da un gruppo di aziende l'OMG (Object Management Group), che ha specificato una architettura denominata CORBA (Common Object Request Broker) che si fonda su i seguenti tre concetti: 
     
  • Modello Object Oriented
  • Sistema di elaborazione aperto e distribuito
  • Progettazione per componenti software riutilizzabili
Oggi ormai Corba (versione 2.2) è entrato in una fase adulta in cui sempre più aziende sopratutto del settore telecomunicazioni lo stanno adottando e molti consolidati prodotti che lo implementano sono disponibili sul mercato.

Qualcuno lo vuole candidare persino come l'erede di HTTP, ma questa é un'altra storia ... Lasciando stare la fantascienza, CORBA potrá occupare sicuramente occupare lo spazio dedicato all'integrazione dei sistemi eterogenei che oggi la metafora del WEB ha occupato.

Client Server Tradizionale 
vs
Corba
 
Vediamo adesso le parti che compongono compongono l'architettura base di CORBA.
 
ORB: Object Request Broker.
Se al centro dell'architettura cliente-server c'era una decomposizione funzionale del software, in CORBA la visione ad oggetti predomina ed il concetto di server si evolve nel concetto di object-server ovverossia di un processo che ha lo scopo di fornire i servizi incapsulati in un "oggetti di rete" (vedremo in seguito cosa si intende). L' ORB ha quindi un duplice scopo: 
     
  • Veicolare, tramite un protocollo standard, le invocazioni dei metodi dell' oggetto di rete dal client verso l' object-server e viceversa.
  • Nascondere al client l' allocazione sulla macchine fisica dei processi server.
Object Request Broker
 
Interazione Client Object Server
 
Esistono quindi in CORBA sempre due ruoli protocollari ben definiti: client e server di oggetti. Questo non vuol dire peró che uno stesso processo possa essere client di uno o piú server ed essere contemporaneamente server per altri oggetti, anzi questa é la norma per sistemi anche di non grandi dimensioni.
La specifica del protocollo dell' ORB definito da CORBA non é vincolata ad un particolare protocollo di rete . Nella versione 2.0 di CORBA viene specificata una mappatura su IP denominata IIOP (Internet Interoperability Protocoll). L'aderenza a questo standard permette ad implementazioni diverse di CORBA (leggi prodotti) di poter interoperare, ovverossia scambiare messaggi sulla rete; cosa che nelle precedenti versioni non per niente scontata anzi tutt'altro che garantita!

Non sono oggetto di specifica le API di accesso al protocollo dell'ORB. Questo ha portato una serie di prodotti che sono in grado di interoperare ma sono totalmente incompatibili a livello di codice.
 
IDL: Interface Definition Language
IDL é il linguaggio che permette di definire i metodi e gli attributi di quelli che nel precedente paragrafo abbiamo definiti "oggetti di rete". La loro descrizione viene denominata "interfaccia" 

IDL è indipendente dallo specifico linguaggio di codifica utilizzato ed indipendente dal sistema operativo/architettura della CPU degli host su cui i client o i server sono in esecuzione. IDL non specifica implementazioni dell'oggetto e supporta l'ereditarietá multipla delle interfacce.

Dati IDL
 

Gli IDL sono organizzati in:

Dentro i moduli possono trovarsi: Come molti linguaggi la parentesi graffe servono a delimitare dichiarazioni complesse e void permette specificare metodi che non ritornano nulla. Un esempio di IDL é definito in seguito.

L' OMG ha specificato le regole per mappare nei vari linguaggi il linguaggio IDL, tra di essi c'è lo SmallTalk,C, il C++, ADA, Java! e persino l'anziano COBOL. Le implementazioni di CORBA posseggono un "compilatore" IDL che traduce l' interfaccia in codice del linguaggio prescelto (tra quelli disponibili)nel caso di Java classi ed interfacce.
Da quanto detto si evince:

Se ci si concentra sul 2 punto si può notare la differenza sostanziale tra l'RMI (vedi MokaByte Apr97 e Nov97) di Java e CORBA: RMI richiede che tutti i processi coinvolti siano scritti in Java! mentre CORBA permette l' integrazione di parti in altri linguaggi magari incapsulando in oggetti IDL le funzionalitá di vecchi sistemi legacy.
 
 

Il repository
vedi interfaccia).Quando un server si avvia come prima cosa si registra nel repository per l'insieme delle istanze degli oggetti che gestisce.

Cosa succede quanto un Client effettua una chiamata.
 

 
Schema di Interazione Client-Object Server

Si possono quindi individuare due approcci nell' interfacciamento all'ORB che possono essere realizzati in maniera indipendente dal client e dal server: Il primo approccio, più semplice da realizzare come vedremo in seguito , richiede la conoscenza dell'IDL dell' oggetto a tempo di compilazione. Il secondo approccio, più flessibile ma complesso, permette di invocare a run time metodi di oggetti la cui definizione non era conosciuta a tempo di compilazione.
 

Un pò di pratica.
Vediamo adesso cosa vuol dire in pratica scrivere un client ed un server in Java che colloquino tramite un broker. Ci riserveremo in seguito di ritornare sui concetti precedentementi esposti per trattarli più in dettaglio.

Non si púo fare un esempio senza riferirsi ad uno specifico prodotto. Il pacchetto da me utilizzato per l' implementazione è ORBIXWEB di IONA per windows commercializzato in Italia da AIS. E'possibile scaricare una versione di prova, pienamente funzionante ma con licenza limitata nel tempo presso il sito di IONA.
L'irlandese IONA é leader di mercato insieme alla concorrente francese VISIGENIC(adesso acquistata da Borland) che produce VISIBroker.La scelta non si esaurisce naturalmente qui, altri case come SUN e Digital, tanto per citarne qualcuna, producono broker. Sono naturalmente disponibili persino dei broker freeware!

L' oggetto di rete che andiamo implementare è una semplice matrice in cui è possibile leggere/scrivere dei valori in una determinata cella.

Interfaccia dell' oggetto Grid.

Vediamo l' interfaccia IDL che la descrive:

/**

 * Descrizione dell'interfaccia all'oggetto griglia matrice bidimensionale.

 *

 */

// grid.idl

interface grid {

        readonly attribute short height;  // height=numero di righe

        readonly attribute short width;   // width =numero di colonne

        // IDL operations

        // imposta il valore dell'elemento [n,m]:

        void set(in short n, in short m, in long value);

        // legge il valore dell'elemento [n,m]:

        long get(in short n, in short m);

};

Come vedete il linguaggio é abbastanza semplice, quasi spartano e molto lontano dalle astrusità di altri linguaggi esoterici per la descrizione dei dati come ASN1 (Abstrac Sintax Notation One) utilizzata da protocolli di gestione come SNMP o CMISE. Rimandiamo alla prossima puntatata una descrizione completa del linguaggio IDL.

L'oggetto definito ha due attributi che definiscono numero di righe e di colonne della matrice, essi sono in sola lettura (readonly) di tipo short che viene mappato nel tipo Java short.
Ci sono poi due metodi get e set che permettono di leggere e di scivere un valore nella matrice, il tipo IDL long é mappato sul long di Java. Il metodo set non restituisce nulla, il metodo get restituisce un long.

Questa file di descrizione viene compilato dal comando di OrbixWeb dato al prompt dos:

<IDL grid>
che produce due insiemi di file: Per completezza bisogna aggiungere che ORBIXWeb genera anche un altro set di classi (che IONA raccomanda di usare nella maggior parte dei casi) per l' implementazione del server: le TIE class, dal prefisso _TIE_ che appare nelle classi generate.
Questo approccio,non specificato da OMG, non segue il modello dell' ereditarietà ma piuttosto un modello di delega in cui la TIE class implementa il comportamento generico del server e usa un'altra classe (fornita dal programmatore ed "agganciata" all' istanziazione dal costruttore della tie class) per implementare gli specifici metodi dell' interfaccia.

Altre classi di supporto vengono inoltre create per la codifica/decodifica dai tipi IDL a quelli Java (Holder class) e per interaggire con l'ORB (Helper class)

Come già detto esistono diversi modi per utilizzare il protocollo dell'ORB. Quello qui descritto che si basa sulle classi generate da IDL è quello detto "statico".In alternativa è possibile usare un metodo detto "dinamico" in cui si implementa ( per la parte server) e si interaggisce (per la parte client) andando direttamente sugli strati protocollari base di interfaccia ed accedendo al repository degli oggetti. Questo consente di interaggire con oggetti la cui struttura non é conosciuta durante la codifica ma che viene letta ed usata a run-time.

Dal punto di vista architetturale, IONA ha scelto di implementare il protocollo lato client tramite librerie di classi, mentre sulla macchina che ospita i server utilizza un Deamon che gestisce i vari object server. In altre implementazioni non è detto che sia rispettato questo schema.

Implementazione del Client.
Vediamo un client che utilizza le classi generate da IDL. Esso é molto semplice: prende dal main come parametro in linea l'indirizzo del host che ospita un Deamon CORBA, si connette all' object server "Grid" da esso ospitato e si "accontenta" di utilizzare l'unico oggetto di tipo Grid messogli a disposizione.

Import org.omg.CORBA.ORB; // classi del broker

Import IE.IONA.OrbixWeb._CORBA;

public class Client {

   public static void main(String args[]) {

"Questa chiamata inizializza il broker. Sono possibili anche chiamate con argomenti che permettono ad esempio di selezionare il protocollo: IOOP che permette di interoperare con altri ORB aderenti alle specifiche CORBA 2.0 o quello proprietario di Orbix (IIOP è il default per ORBIXWeb 3.0)"
      org.omg.CORBA.ORB.init();
"Grid é l'interfaccia Java generata automaticamente dal compilatore IDL ed implementata da _GridStub. Quest' ultima é detta in gergo classe proxy poiché si preoccupa di rendere trasparente il colloquio protocollare con il server."
      Grid grid = null;

      String svrHost=null;

      short h=0,w=0;

      int v=0;

      SrvHost = new String(args[0]);

"Per ottenere una istanza di tipo Grid si usa il metodo bind della classe GridHelper generata da IDL. Ottenuto l'eccesso all'oggetto si possono referenziare anche altri oggetti contenuti nel server senza effettuare più la bind (non è questo il caso dell' esempio). Il blocco seguente è gestito dentro una try poichè tutte le chiamata alla classe proxy sollevano delle eccezioni che per semplicità vengono trattate nell' esempio in un unico blocco"
try {

      grid = GridHelp.bind( ":Grid",svrHost);

"Adesso l'oggetto si può manipolare come se fosse in locale"
      w = grid.width();

      h =  grid.height();

      System.out.println("La grigia gestita  dal server :GrdSrv nel nodo "

                           +srvHost+" ha dimensioni "+w+"x"+h);
"Imposto un valore sulla grigia"

     grid.set( (Short) 2, (Short) 4, 123);
"Leggo un valore dalla grigia"

        v = grid.get( (short)2 (short) 4);

        System.out.println(" in posizione 2,4 c'è il valore"+v);

}catch (SystemmException e) {

       System.out.println("eccezione durante la gestione dell'oggetto grid:"+e.toString())

}// end catch

}// end main

}// end class

Vediamo adesso il server:
Il Server.

Il package che implementa il server contiene la definizione di due classi:

package gridtest;

import IE.Iona.OrbixWeb._OrbixWeb;

import IE.Iona.OrbixWeb._CORBA;

import org.omg.CORBA.ORB;

public class GridServer {

  public static void main(String args[]) {

    grid gridImpl = null;

    org.omg.CORBA.ORB orb = org.omg.CORBA.ORB.init(); // inizializzo il broker

try {

"Viene creato un oggetto di tipo grid dalla classe GridImplementation "

     gridImpl = new GridImplementation((short)100,(short)100);
"Dichiara all'ORB Deamon di essere pronto. La chiamata è bloccante da essa si ritorna solo perchè è stato ordinato lo shutdown del server, o per errore. La stringa Grid é il nome con cui il server Grid si regista ed é lo stesso che deve essere usato nella bind fatta dal client"

     IE.Iona.OrbixWeb._CORBA.Orbix.impl_is_ready("Grid");

     System.out.println("Shutting down del server...");

     orb.disconnect(gridImpl);

    }

    catch(org.omg.CORBA.SystemException e) {

      System.out.println("Errore in implementazione di GRID" + e.toString());

      System.exit(1);

    }

    System.out.println ("Server terminato....");

  }// end main

}// end class

class GridImplementation extends _gridImplBase {

  public short m_height;  // numero delle righe

  public short m_width;   // numero delle colonne

  public int m_a[][];     // matrice bidimendionale dei valori dell'oggetto di tipo Grid

  public GridImplementation(short height, short width)

  {

    m_a = new int[height][width]; // allocata  la matrice bidimensionale

    m_height = height; // imposta righe

    m_width = width;   // imposta colonne

  }

 public short height() {

   return m_height;

  }

  public short width(){

    return m_width;

  }

public void set(short x, short y, int value) {

m_a[y][x] = value;

}

"Notare come il valore di ritorno long dell'IDL si mappa su in int di Java"

public int get(short x, short y) {

int t = m_a[y][x];

return t;

}

}

Conclusioni.
Per questa puntata è tutto! Abbiamo dato una panoramica generale su CORBA e cosa voglia dire scrivere applicazioni CORBA in Java. Nella prossima puntata approfondiremo il linguaggio IDL e gli altri moduli che costituiscono l' OMA (Object Management Architetture) di CORBA.
 
 
 
  
 

MokaByte rivista web su Java

MokaByte ricerca nuovi collaboratori
Chi volesse mettersi in contatto con noi può farlo scrivendo a mokainfo@mokabyte.it