Prečítajte si InputStream pomocou zásuvky servera Java

1. Prehľad

Na odosielanie a prijímanie údajov v sieti často používame zásuvky. Sokety nie sú ničím iným ako kombináciou adresy IP a čísla portu, ktoré môžu jedinečným spôsobom identifikovať program bežiaci na danom počítači.

V tomto výučbe si ukážeme, ako môžeme čítať údaje, ktoré sa nám zasielajú cez soket.

2. Čítanie údajov zo zásuvky

Predpokladajme, že máme základné znalosti o programovaní zásuviek.

Teraz sa budeme hlbšie venovať čítaniu údajov na porte, na ktorom náš server počúva.

Najprv musíme deklarovať a inicializovať ServerSocket, pätica, a DataInputStream premenné:

ServerSocket server = nový ServerSocket (port); Socket socket = server.accept (); DataInputStream in = nový DataInputStream (nový BufferedInputStream (socket.getInputStream ()));

Všimnite si, že sme sa rozhodli zabaliť zásuvky InputStream v DataInputStream. To nám umožňuje čítať riadky textu a primitívne dátové typy Java prenosným spôsobom.

To je pekné, pretože odteraz, ak poznáme typ údajov, ktoré dostaneme, môžeme použiť špecializované metódy ako readChar (), readInt (), readDouble ()a readLine ().

Môže to však byť náročné, ak nie je vopred známy typ a dĺžka údajov.

V takom prípade namiesto toho dostaneme prúd bajtov zo soketu pomocou nižšej úrovne čítať() funkcie. V tomto prístupe však existuje malý problém: Ako zistíme dĺžku a typ údajov, ktoré dostaneme?

Pozrime sa na tento scenár v nasledujúcej časti.

3. Čítanie binárnych údajov zo zásuvky

Pri čítaní dát v bytoch si musíme definovať vlastný protokol pre komunikáciu medzi serverom a klientom. Najjednoduchší protokol, ktorý môžeme definovať, sa nazýva TLV (Type Length Value). To znamená, že každá správa zapísaná do soketu je vo forme hodnoty dĺžky typu.

Každú odoslanú správu teda definujeme ako:

  • A 1 bajt znak, ktorý predstavuje dátový typ, napríklad s pre String
  • A 4 bajt celé číslo, ktoré označuje dĺžku údajov
  • A potom skutočné údaje, ktorých dĺžka bola práve uvedená

Keď klient a server nadviažu spojenie, každá správa bude mať tento formát. Potom môžeme napísať náš kód, ktorý analyzuje každú správu a číta n bajtov údajov konkrétneho typu.

Pozrime sa, ako to môžeme implementovať na jednoduchom príklade s a String správa.

Najprv musíme zavolať readChar () funkcie, načítať typ údajov a potom volať readInt () funkcia na čítanie jeho dĺžky:

char dataType = in.readChar (); int dĺžka = in.readInt ();

Potom si musíme prečítať údaje, ktoré dostávame. Je tu potrebné poznamenať, že: čítať() táto funkcia nemusí byť schopná načítať všetky údaje pri jednom hovore. Musíme teda zavolať čítať() v slučke while:

if (dataType == 's') {byte [] messageByte = nový bajt [dĺžka]; boolovský koniec = nepravda; StringBuilder dataString = nový StringBuilder (dĺžka); int totalBytesRead = 0; while (! end) {int currentBytesRead = in.read (messageByte); totalBytesRead = currentBytesRead + totalBytesRead; if (totalBytesRead = dĺžka) {end = true; }}}

4. Kód klienta na odosielanie údajov

A čo kód na strane klienta? V skutočnosti je to celkom jednoduché:

char type = 's'; // s pre reťazec String data = "Toto je reťazec s dĺžkou 29"; byte [] dataInBytes = data.getBytes (StandardCharsets.UTF_8); out.writeChar (typ); out.writeInt (dataInBytes.length); out.write (dataInBytes);

To je všetko, čo náš klient robí!

5. Záver

V tomto článku sme diskutovali o tom, ako čítať údaje zo zásuvky. Pozreli sme sa na rôzne funkcie, ktoré nám pomáhajú čítať údaje konkrétneho typu. Tiež sme videli, ako čítať binárne údaje.

Celú implementáciu tohto tutoriálu nájdete na GitHub.


$config[zx-auto] not found$config[zx-overlay] not found