This page presents a very simple client to access a server that implements the file system we developed in Slice for a Simple File System. The PHP code shown here hardly differs from the code you would write for an ordinary PHP program. This is one of the biggest advantages of using Ice: accessing a remote object is as easy as accessing an ordinary, local PHP object. This allows you to put your effort where you should, namely, into developing your application logic instead of having to struggle with arcane networking APIs.
We now have seen enough of the client-side PHP mapping to develop a complete client to access our remote file system. For reference, here is the Slice definition once more:
To exercise the file system, the client does a recursive listing of the file system, starting at the root directory. For each node in the file system, the client shows the name of the node and whether that node is a file or directory. If the node is a file, the client retrieves the contents of the file and prints them.
The body of the client code looks as follows:
The program first defines the
listRecursive function, which is a helper function to print the contents of the file system, and the main program follows. Let us look at the main program first:
- The client first creates a proxy to the root directory of the file system. For this example, we assume that the server runs on the local host and listens using the default protocol (TCP/IP) at port 10000. The object identity of the root directory is known to be
- The client down-casts the proxy to the
Directoryinterface and passes that proxy to
listRecursive, which prints the contents of the file system.
Most of the work happens in
listRecursive. The function is passed a proxy to a directory to list, and an indent level. (The indent level increments with each recursive call and allows the code to print the name of each node at an indent level that corresponds to the depth of the tree at that node.)
listRecursive calls the
list operation on the directory and iterates over the returned sequence of nodes:
- The code uses
checkedCastto narrow the
Nodeproxy to a
Directoryproxy, and uses
uncheckedCastto narrow the
Nodeproxy to a
Fileproxy. Exactly one of those casts will succeed, so there is no need to call
checkedCasttwice: if the
Directory, the code uses the proxy returned by
checkedCastfails, we know that the Node is-a File and, therefore,
uncheckedCastis sufficient to get a
In general, if you know that a down-cast to a specific type will succeed, it is preferable to use
uncheckedCastdoes not incur any network traffic.
- The code prints the name of the file or directory and then, depending on which cast succeeded, prints
"(file)"following the name.
- The code checks the type of the node:
- If it is a directory, the code recurses, incrementing the indent level.
- If it is a file, the code calls the
readoperation on the file to retrieve the file contents and then iterates over the returned sequence of lines, printing each line.
Assume that we have a small file system consisting of a two files and a a directory as follows:
A small file system.
The output produced by the client for this file system is:
Note that, so far, our client is not very sophisticated:
- The protocol and address information are hard-wired into the code.
- The client makes more remote procedure calls than strictly necessary; with minor redesign of the Slice definitions, many of these calls can be avoided.