Fatty Bolger
Fatty Bolger

Reputation: 1

TCP Java question

I am learning about using sockets with Java and have encountered a problem for a script I wish to write. I have written a basic script for a client and a server and now wish to expand on it. (It's more or less the one specified here : Link to Oracle tutorial).

Now I wish to adapt this program to have it do a few things differently, I'd like the server, on connection of the client, to send a list of all files in the home directory to the server, the client then picks one out and details of that file are sent back to the client (the equivalent of an ls -a in terminal). Then the client can type yes or no, deciding if they want to download the file or not.

I think it should be simple enough, so I'd like to do it myself so that I can learn, can anyone tell me how I can begin, or some examples I can look at, because I have tried searching and can find nothing.

Thanks very much.

Edit : How can I send a list of the files in a directory, is there a function to get this list ?

Upvotes: 0

Views: 434

Answers (2)

jkj
jkj

Reputation: 2611

The protocol is of importance here. Either you can design a text protocol like the KnockKnockProtocol in the example. e.g:

client: LIST
server: FILES foo.txt bar.txt
client: DETAILS bar.txt
server: DETAILS bar.txt 123421 0644 myuser mygroup
client: GET bar.txt
server: FILEDATA bar.txt <base64-encoded content or such>
client: QUIT

But there are already many of those around, designing good protocols is hard and it is quite easy to write bugs in parsers etc. It's generally not worth it.

But... You use java for both client and server and java can serialize objects so you can send whole objects through network streams. That way you don't have to bother with parsing issues.

Just read the network socket through ObjectInputStream and write through ObjectOutputStream. That way you can have classes that model the requests and responses of your protocol.

public interface Request implements Serializable {
}

public class ListFilesRequest implements Request {
}

public class FileDetailsRequest implements Request {
    public String fileName;
}

public class DownloadFileRequest implements Request {
    public String fileName;
}

public interface Response implements Serializable {
}

public class FileListResponse implements Response {
    public String[] fileNames;
}

public class FileDetailsResponse implements Response {
    public String fileName;
    public int fileSize;
    public int fileMode;
}

public class FileDataResponse implements Response {
    public String fileName;
    public byte[] fileData;
}

Then server could do something like:

ObjectInputStream objInput = new ObjectInputStream(mySocket.getInputStream());
ObjectOutputStream objOutput = new ObjectOutputStream(mySocket.getOutputStream());
Object requestObject = objInput.readObject();
Response responseObject = null;

if (requestObject instanceOf ListFilesRequest) {
    FileListResponse response = new FileListResponse();
    response.fileNames = new String[] { "foo.txt", "bar.txt" };
    responseObject = response;
}
else if (requestObject instanceOf FileDetailsRequest) {
    FileDetailsRequest request = (FileDetailsRequest)requestObject;
    String fileName = request.fileName;
    ...
}

objOutput.writeObject(responseObject);

...or something like this.

Upvotes: 0

d-live
d-live

Reputation: 8036

Shouldnt be difficult once you have set up a basic request/response example. You basically will have to set up a switch case kind of construct inside the server that will decide what to send based upon what it recieves.

Something like

if recievedCommand = Nothing
   Send File List
if recievedCommand = FileName
   Send File info
...

And so on. Hope this gets your ball rolling

Upvotes: 1

Related Questions