Shob Logo Última Atualização: 8 de dezembro de 2002 18:34 BRST

Tutorial

Esse exemplo trata de uma aplicação de leilão muito simplificada. Nosso objeto compartilhado (Offer) terá apenas quatro operações. Primeiro iremos definir a interface para o objeto compartilhado. Note que a interface deve extender java.io.Serializable e que todos os seus métodos devem lançar br.shob.ShobException.

   1:package auction.core;
   2:
   3:import br.shob.ShobException;
   4:
   5:public interface Offer extends java.io.Serializable {
   6:
   7:    public String getName() throws ShobException;
   8:    public double getValue() throws ShobException;
   9:    public String getWinner() throws ShobException;
  10:    public void doBid(double value, String user) throws InvalidBidException, ShobException;
  11:}
  12:

Uma vez compartilhado o objeto só poderá ser acessado através de uma referência. Podemos utlizar a ferramenta que é distribuída junto com o pacote, o Configurator. Para gerar a referência precisamos definir o seu nome, o arquivo onde serão guardadas as suas configurações, e quais métodos são de escrita. O configurator irá gerar um arquivo XML contendo todas essas informações. o Configurator recebe como parâmetro o arquivo .class com a interface compilada.

Veja aqui o XML gerado pelo Configurator.

A partir do arquivo de configuração podemos gerar a referência propriamente dita. Para isso utilizamos outra ferramenta, também distribuída com o pacote, o shobc. Ele recebe como parâmetro o arquivo XML gerado pelo Configurator e o .class da interface, e cria um arquivo .java com o código fonte da referência, que pode ser compilado junto com a aplicação.

Uma característica importante dessa referência é que o único vínculo entre ela e a classe original é a interface implementada por ambas. Por isso, a mesma referência pode ser utilizada para manipular implementações diferentes da mesma interface, o que pode ser de grande valia.

Veja aqui o código fonte da nossa referência. É importante ressaltar que este código não precisa ser alterado e nem mesmo entendido, ele está sendo mostrado apenas de maneira ilustrativa, assim como o XML mostrado acima.

 Agora iremos realmente implementar o objeto, como faríamos numa aplicação padrão. Podemos perceber que a classe abaixo não prevê um uso distrbuído, ela é implementada como se o objeto fosse utilizado apenas localmente.

   1:package auction.server;
   2:
   3:import auction.core.*;
   4:
   5:public class OfferImpl implements Offer {
   6:
   7:    private String name;
   8:    private double value;
   9:    private String winner;
  10:
  11:    public OfferImpl(String name, double value, String winner) {
  12:        this.name = name;
  13:        this.value = value;
  14:        this.winner = winner;
  15:    }
  16:
  17:    public String getName() {
  18:        return name;
  19:    }
  20:
  21:    public double getValue() {
  22:        return value;
  23:    }
  24:
  25:    public String getWinner() {
  26:        return winner;
  27:    }
  28:
  29:    public void doBid(double value, String user) throws InvalidBidException {
  30:        if(value < getValue()) {
  31:            throw new InvalidBidException("Invalid bid. " + value + " < " + getValue());
  32:        }
  33:        this.value = value;
  34:        this.winner = user;
  35:    }
  36:}
  37:

 Nossa aplicação de exemplo é bem simples: o servidor compartilha apenas um objeto do tipo Offer e deixa que os clientes façam lances nessa oferta.

   1:package auction.server;
   2:
   3:import br.shob.*;
   4:import auction.core.*;
   5:
   6:public class AuctionServer {
   7:
   8:    public final static void main(String args[])
   9:        throws Exception {
  10:
  11:        //cria um SharedSpace
  12:        SharedSpace shob = new SharedSpace("localhost", 0);
  13:
  14:        //connecta o SharedSpace ao servidor de nomes
  15:        shob.connect("localhost", 5000);
  16:
  17:        //cria uma Offer
  18:        Offer offer = new OfferImpl("potato", 10.0, null);
  19:
  20:        //compartilha a Offer
  21:        shob.share("offer1", offer, "auction.core.OfferReference");
  22:    }
  23:}
  24:

Os clientes que participam do leilão também são extremamente simples, eles apenas lêem o valor da oferta e realizam um lance maior.

   1:package auction.client;
   2:
   3:import br.shob.*;
   4:import auction.core.*;
   5:
   6:public class AuctionClient {
   7:
   8:    public final static void main(String args[])
   9:        throws Exception {
  10:
  11:        //cria um SharedSpace
  12:        SharedSpace shob = new SharedSpace("localhost", 0);
  13:
  14:        //connecta o SharedSpace ao servidor de nomes
  15:        shob.connect("localhost", 5000);
  16:
  17:        //pega uma Offer
  18:        Offer offer = (Offer)shob.get("offer1");
  19:
  20:        System.out.println("Offer Name:   " + offer.getName());
  21:        System.out.println("Offer Value:  " + offer.getValue());
  22:        System.out.println("Offer Winner: " + offer.getWinner());
  23:
  24:        double bid = offer.getValue() + 10;
  25:        System.out.println("Bid: " + bid);
  26:        offer.doBid(bid, "user1");
  27:        System.out.println("Offer Value:  " + offer.getValue());
  28:        System.out.println("Offer Winner: " + offer.getWinner());
  29:    }
  30:}
  31:

 Com esse exemplo conseguimos mostrar quias são os passos necessários para se criar uma aplicação que utliza o shob. A dificuldade para se criar uma aplicação distribuída não é muito maior que a dificuldade para se criar uma aplicação local, o que mostra todo o poder do shob.