Historically,
network
programming has been error-prone, difficult, and complex.
The
programmer had to know many details about the network and sometimes even the
hardware. You usually needed to understand the various “layers” of
the networking protocol, and there were a lot of different functions in each
different networking library concerned with connecting, packing, and unpacking
blocks of information; shipping those blocks back and forth; and handshaking.
It was a daunting task.
However,
the concept of networking is not so difficult. You want to get some information
from that machine over there and move it to this machine here, or vice versa.
It’s quite similar to reading and writing files, except that the file
exists on a remote machine and the remote machine can decide exactly what it
wants to do about the information you’re requesting or sending.
One
of Java’s great strengths is painless networking. As much as possible,
the underlying details of networking have been abstracted away and taken care
of within the JVM and local machine installation of Java. The programming model
you use is that of a file; in fact, you actually wrap the network connection (a
“socket”) with stream objects, so you end up using the same method
calls as you do with all other streams. In addition, Java’s built-in
multithreading is exceptionally handy when dealing with another networking
issue: handling multiple connections at once.
This
chapter introduces Java’s networking support using easy-to-understand
examples.