Interfacing to External Services

Although the TCP subroutines are quite useful for communicating between A-Shell processes, they are probably even more useful for communicating with the "outside world". As noted previously, most of the important services on the Internet are based on well-documented socket protocols. This means that you can use TCPX or TCPCLI to write client programs which can talk to Internet servers, and you can use TCPX or TCPSRV to write server programs that standard clients can use to talk to you.

As a trivial but instructive example of talking to an Internet server, you can fetch raw web pages from any Internet web server using code similar to the following:

map1 BUFFER,S,1024

map1 HOSTNAME,S,80

map1 SOCKPORT,F

map1 TIMER,F,6,5000      ! 5 second timeout

map1 FLAGS,F,6

 

HOSTNAME = "www.microsabio.com"         ! web site or IP addr (without http://)

SOCKPORT = 80                           ! standard http port

 

FLAGS = 1     ! blocking mode

xcall TCPX,9,STATUS,BUFFER,SOCKPORT,FLAGS,TIMER,HOSTNAME    ! connect to site

   if STATUS < 0 goto ERROR

 

BUFFER = "GET /index.html" + chr(13) + chr(10)              ! (must have CFLF!)

FLAGS = len(BUFFER)                                         ! # bytes to send

 

xcall TCPX,2,STATUS,BUFFER,SOCKPORT,FLAGS,TIMER             ! send GET command

   if STATUS <= 0 goto ERROR

 

LOOP:                       ! retrieve the home page, one buffer at a time

   FLAGS = 0                ! retrieve one packet at a time (up to BUFFER size)

   xcall TCPX,4,STATUS,BUFFER,SOCKPORT, FLAGS,TIMER

   ! depending on how remote side closes socket, we may get STATUS 0 or -10054...

   if STATUS = 0 or STATUS = -10054 goto DONE               ! remote side closed

   if STATUS < 0 goto ERROR  

 

      <process page text in BUFFER>

 

   goto LOOP

 

DONE:

   xcall TCPX,6,STATUS,BUFFER,SOCKPORT   ! close

 

END

 

The GET command syntax above is an HTTP 1.0 "Simple Request", which is a generally deprecated form, although nearly all web servers will support it. Refer to the RFCs for HTTP (such as RFC 2616) for full specifications on the HTTP protocol. The point of the example is just to demonstrate how simple (and text-oriented) many of these Internet socket-based protocols can be.

A slightly more complicated example can be seen by looking at the detailed log file created by the EMAILX.SBX routine, which will show the exchange between a mail client and an SMTP server. As with the HTTP protocol, SMTP is based on simple CRLF-terminated text commands.

If you need design a protocol for a server that will be accessed by "foreign" (non-A-Shell) clients, you may want to follow the model of protocols such as HTTP and SMTP and base them on CRLF-terminated text lines. Although human-readable text-based protocols may seem slightly less "efficient", this is really not much of a concern because of the substantial packet overhead suffered by small packets. For example, the smallest possible Ethernet IPv4 packet is 68 bytes, so there is little point in trying to compress your command lengths down to a few bytes, unless you can pack many of them together in a single packet. On the other hand, there are several significant advantages to text-oriented protocols, including:

• They are easier to document.

• They are easier to debug. (A simple text log of all data sent and received tells all.)

• You can test the server side using Telnet as a client.