Jednostavne su aplikacije peer-to-peer

Rečeno je da Kazaa, peer-to-peer (P2P) aplikacija za dijeljenje datoteka, uzrokuje više mrežnog prometa od bilo koje druge aplikacije. Web stranica Kazaa navodi da je imala više od 385 000 000 preuzimanja! Za usporedbu, pregledao sam najpopularnija preuzimanja Download.com, koja Ad Aware navodi kao najpopularnije preuzimanje, sa samo 117 000 000 preuzimanja. Iz 25 najboljih preuzimanja Download.com prepoznao sam 11 P2P aplikacija. Samo iz ovih opažanja, P2P aplikacije očito rastu u popularnosti. No dijeljenje datoteka nije jedina vrsta P2P aplikacija. Većina operacija tipične aplikacije za razmjenu trenutnih poruka je P2P. Ostali primjeri su forumi i distribuirane baze podataka. A popis samo nastavlja rasti.

Da biste stvorili P2P aplikacije poput ovih, morate imati sredstva za otkrivanje i interakciju s drugim vršnjacima. Većina poteškoća uključenih u stvaranje P2P aplikacija povezane su s održavanjem mreže vršnjaka, formatiranjem i prosljeđivanjem poruka, otkrivanjem drugih vršnjaka i drugim sličnim problemima. Projekt Jxta i njegovo vezivanje za Java rješavaju ove aspekte vaše aplikacije. Korištenjem Jxte možete se usredotočiti na svoju aplikaciju, a ne na generička P2P pitanja.

Jxta je skraćena verzija riječi juxtapose,što znači rame uz rame. Vodič za programera Jxta definira Jxta kao "otvorenu računalnu platformu dizajniranu za P2P računanje". Nije specifičan ni za jednu platformu ni za bilo koji programski jezik. Zamišljen je u Sun Microsystems, a pušten je zajednici otvorenog koda na održavanje i rast. Zajedno s izdanjem izdana je početna Java implementacija. U ovom sam članku usredotočen na tu implementaciju dok raspravljam o tome kako koristiti Jxta u Java okruženju. Također pokrivam šest najčešćih operacija Jxta aplikacija implementiranih u Javi i predstavljam alate potrebne za pisanje vlastitih P2P aplikacija. Nakon čitanja ovog članka, nadam se da ste shvatili koliko lako i uzbudljivo može biti stvaranje P2P aplikacija. P2P aplikacije i dalje će rasti ne samo u popularnosti, već iu raznolikosti,i sutrašnji programeri moraju početi učiti te tehnologije već danas kako bi ostali na vrhu.

Java i Jxta

Prvi korak prema korištenju Jxte je preuzimanje sa stranice za preuzimanje Jxte. Kao što će se složiti većina čitatelja, ponekad je projekte s otvorenim kodom teško nabaviti i konfigurirati za upotrebu. Jxta je primjer sjajnog projekta otvorenog koda koji je također vrlo lako odmah preuzeti i koristiti. Ako vam je teško i trebate više informacija o preuzimanju i korištenju Jxte, pogledajte Vodič za programera Jxta.

Kada prvi put pokrenete aplikaciju s omogućenim Jxta-om iz novog direktorija, dobit ćete GUI konfigurator.

Što je zapravo vršnjak? Prema Danielu Brookshireu (poznatom počinitelju Jxte i takozvanom "prvaku"), to je "virtualna komunikacijska točka", na kojoj različiti vršnjaci mogu raditi na istom uređaju. Uređaj nije ograničen na računalo; to može biti mobitel, poslužitelj ili čak jednostavna stavka poput senzora. Postoje posebni vršnjaci, njih dvoje kojih moramo biti svjesni su sastanak i štafeta. Randevvous peer omogućava vršnjacima da komuniciraju izvan opsega lokalne podmreže, a relejni peer koristi se za prenošenje informacija kroz vatrozid.

Krenimo od prolaska kroz šest najčešćih operacija Jxta aplikacija, kako je definirano u "Troškovi korištenja Jxte" (IEEE Computer Society, rujan 2003.). Dolje su navedeni redoslijedom kojim se obično javljaju.

  1. Pokretanje Jxte: Pokretanje Jxte prilično je jednostavno i jednostavno je stvar nekoliko redaka koda.
  2. Pridruživanje vršnjačkoj grupi: Vršnjačka grupa je skup vršnjaka koji imaju zajednički skup interesa koji su grupirani. U ovom članku pokrivam pridruživanje postojećih grupa vršnjaka i stvaranje novih.
  3. Objavljivanje reklama: Reklame, jednostavno rečene, ono su što je Jxta. Jxta koristi oglašavanje za otkrivanje vršnjaka, grupa vršnjaka i drugih resursa na način neovisan o platformi. Dalje u ovom članku raspravljam o čitanju, stvaranju i slanju novih oglasa.
  4. Otvaranje ulazne cijevi: Lula je jedan mehanizam koji vršnjaci koriste za međusobnu komunikaciju. Cijevi su "virtualni komunikacijski kanali " - virtualni u tome što korisnici cijevi ne znaju stvarnu adresu drugog kolega. U članku o cijevima u ovom članku raspravljam o korištenju cijevi za slanje poruka.
  5. Otkrivanje drugih izvora vršnjaka: Prije nego što možete komunicirati s drugim vršnjacima, prvo morate pronaći neke, o čemu ću također razgovarati.
  6. Otvaranje izlazne cijevi: Izlazne cijevi koriste se za slanje poruka drugim vršnjacima. Postoje dvije klase izlaznih cijevi: točka-točka ili jedna prema jedna i širenje ili jedna prema više.

Sad kad znate kamo će vas odvesti ovaj članak, započnimo naše putovanje.

Grupe vršnjaka

Vršnjačke skupine su jednostavno kolekcija vršnjaka s nekim skupnim zajedničkim interesima. Vršnjačke skupine, poput vršnjaka, mogu pružati usluge, no usluga vršnjačke grupe ne mora nužno ovisiti o određenom vršnjaku koji mu ispunjava zahtjeve. Sve dok jedan vršnjak u grupi pruža uslugu, tada je usluga dostupna. Svaki je vršnjak član svjetske vršnjačke skupine, a također, obično, neto vršnjačke grupe i može odabrati da se pridruži i napusti druge grupe po svojoj volji. Koji je motiv za stvaranje vršnjačkih grupa? Evo nekoliko razloga:

  • Održavanje sigurne regije: ako imate sigurnu grupu vršnjaka, vršnjaci u grupi ne moraju izlagati svoje kritične podatke.
  • Pružanje zajedničkih usluga: Obično će mnogi vršnjaci htjeti koristiti / pružiti iste usluge kao i drugi vršnjaci, pa to učiniti u grupi ima smisla. Na primjer, možete pružiti pisač ili uslugu distribuirane baze podataka svim vršnjacima u grupi.
  • Ograničeni opseg ID-a: Imena cijevi podudaraju se s grupom u kojoj su stvorena. Ako dvije cijevi imaju isto ime, ali nisu stvorene u istoj grupi, tada nema problema s njihovim adresiranjem.

Ispitajmo kako možemo stvoriti i pridružiti se grupi vršnjaka. Metode koje pruža PeerGroupsučelje navedene su u nastavku.

  • newGroup(Advertisement pgAdv): obično se koristi za instanciranje grupe koja već postoji s otkrivenim oglasom grupe
  • newGroup(PeerGroupID gid, Advertisement impl, String name, String description): obično se koristi za konstrukciju novih grupa vršnjaka
  • newGroup(PeerGroupID gid): koristi se za instanciranje postojeće i objavljene peer grupe sa samo ID peer grupe ( gid)

Stvaranje grupa vršnjaka

Stvaranje osnovne grupe vršnjaka relativno je jednostavno. Pogledajmo neki kod:

try { //We will create a new group based on the netPeerGroup so let's copy its //impl advertisement and modify it. ModuleImplAdvertisement implAdv = netPeerGroup.getAllPurposePeerGroupImplAdvertisement(); myPeerGroup = netPeerGroup.newGroup( null, //Create a new group id for this group. implAdv, //Use the above advertisement. "Group name", //This is the name of the group. "Group description" //This is the description of the group. );

System.out.println("---Peer group created successfully, id: " + myPeerGroup.getPeerGroupAdvertisement().getID() ); //Now that the group is created, it is automatically published and stored locally, //but we need to publish it remotely so other peers can discover it. discoveryService.remotePublish( myPeerGroup.getPeerGroupAdvertisement() ); System.out.println("---Published peer group advertisement remotely"); } catch (Exception e) { System.out.println("An error occurred"); e.printStackTrace(); }

Poziv za newGroup()stvaranje i objavljivanje grupe u lokalnoj predmemoriji. Najvjerojatnije ćete ovaj oglas htjeti objaviti drugim vršnjacima kada ga napravite, što možete učiniti pozivom remotePublish(). Ovom će se metodom oglašavanje grupe vršnjaka gurnuti drugim vršnjacima. Ako morate biti sigurni da ćete oglas poslati vršnjacima na drugoj podmreži, morate biti sigurni da ste povezani s vršnjakom za sastanak. Da biste to učinili, upotrijebite sljedeći kôd, pod pretpostavkom da je vaš ravnopravni korisnik i da je pravilno konfiguriran:

private void connectToRdv(PeerGroup peerGroup) { if( rdv == null) { //Get the rdv service rdv = peerGroup.getRendezVousService(); } //Make sure that we are connected before proceeding while( !rdv.isConnectedToRendezVous() ) { try { Thread.sleep(5000); } catch (InterruptedException e1) { System.out.println("rdv connect interrupted"); e1.printStackTrace(); } } } 

Pridruživanje vršnjačkim skupinama

Pridružiti se grupi vršnjaka može biti teže nego zapravo je stvoriti. Čak i ako imamo nesigurnu grupu ravnopravnih osoba, i dalje moramo stvoriti vjerodajnice, isprazniti vjerodajnice i poslati ih vjerodajnicama grupi kojoj se pokušavamo pridružiti.

Budući da imamo oglas grupe vršnjaka, moramo stvoriti sve vjerodajnice i pridružiti se grupi. Prije nego što pogledamo joinGroup()metodu, pogledajmo jednu od klasa koju ona koristi, MembershipServiceklasu. Postoje tri metode u MembershipServicekoje smo zainteresirani, posebno apply(), join()i resign(). Metodi prosljeđujemo apply()željenu vrstu provjere autentičnosti i ako je ta vrsta podržana, vraća nam Authenticator. To koristimo da Authenticatorbismo se zapravo pridružili grupi. Prosljeđujemo ga kao argument join()metodi i on potvrđuje naše vjerodajnice. Kada vršnjak želi napustiti grupu, poziv za to resign()olakšava.

Pogledajmo sada joinGroup()metodu:

private void joinGroup() { //Assuming myPeerGroup has been instantiated //before calling this method. System.out.println("Trying to join the peer group"); try { //Create the document that will identity this peer. StructuredDocument identityInfo = null; //No identity information required for our group.

AuthenticationCredential authCred = new AuthenticationCredential( myPeerGroup, //Peer group that it is created in null, //authentication method. ); MembershipService membershipService = myPeerGroup.getMembershipService(); Authenticator auth = membershipService.apply(authCred); //See if the group is ready to be joined. //Authenticator currently makes no distinction between //failed and unfinished authentication. if( auth.isReadyForJoin() ) { Credential myCred = membershipService.join(auth); System.out.println("Joined myPeerGroup"); System.out.println("Group id: " + myPeerGroup.getPeerGroupID() ); } else { System.out.println("Unable to join the group"); } } catch (Exception e) { System.out.println("An error occurred"); e.printStackTrace(); } }

Now that we have successfully joined the group, we are able to employ provided peer group services and send messages to the members. When developing P2P applications, thinking about where you want your peer group boundaries ahead of time will assist you in the long run. Keep in mind that peer group boundaries can span many networks.

The joining process can seem daunting at first, but it is pretty straightforward once you do it a few times. Now it is possible to employ many different methods to secure a peer group—the complexity of the joining process depends on the type of authentication desired. I do not discuss these methods here.

Pipes

As explained earlier, a pipe is a virtual channel of communication between two peers. Pipes can be confusing for beginners because newbies try to relate them to what they already know—sockets. While I discuss pipes, keep in mind that they are much more abstract then sockets.

In the most basic form, there are two types of pipes; input pipes and output pipes. Applications use input pipes to receive information, and output pipes, to send information. Pipes can be used in two addressing modes:

  • Unicast (point-to-point) pipes: These pipes connect one output pipe to a single input pipe, but a single input pipe can receive messages from different output pipes
  • Propagate pipes: These pipes connect a single output pipe to many different input pipes

Pipes are an unreliable, unidirectional, and asynchronous means of communication. Beefed-up implementations of pipes are available that provide reliability, bidirectional capabilities, and secure transit.

To create a pipe, first you must create a pipe advertisement and publish it. Then you need to get the pipe service from the peer group and use it to create the pipe. Each pipe has a pipe ID associated with it, which is used to address the pipe.

To create a new pipe ID, we use the IDFactory in the net.jxta.id package. Here is a sample of how to create and print the ID:

 ID id = IDFactory.newPipeID( peerGroup.getPeerGroupID() ); System.out.println( id.toURI() ); 

Note:peerGroup is the peer group for which you want to create the pipe.

Dakle, dvoje vršnjaka mogu međusobno komunicirati, moraju znati ID-ove cijevi s kojima žele komunicirati. Postoji nekoliko načina kako osigurati da oboje znaju ove informacije:

  • Oba vršnjaka čitaju u istoj cijevi oglas iz datoteke
  • ID cijevi je čvrsto kodiran u aplikacijama
  • Objavite i otkrijte ID cijevi tijekom izvođenja
  • ID cijevi generira se iz dobro poznatog ID-a