How to transfer file using IOUtils.copy through Java Sockets - java

I am currently working with Java Sockets. I have created a server side code and client side code to transfer file through socket. I have successfully transferred the files from client to server with in the same system, but if I tried with the different systems in different platform, then it is not working. The server side and client side codes are given below.
Server side code
public class FileTransferTestServer extends Thread{
private final Socket socket;
public FileTransferTestServer(Socket socket) {
// TODO Auto-generated constructor stub
this.socket = socket;
}
/**
* #param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
try {
ServerSocket serverSocket = new ServerSocket(5000);
Socket socket = serverSocket.accept();
System.out.println("Connection Established with "+socket.getInetAddress().getHostAddress());
new FileTransferTestServer(socket).start();
serverSocket.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public void run(){
try {
InputStream is = socket.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(is));
String buffer = null;
String fileName = null;
if((buffer = br.readLine()) != null){
fileName = buffer;
}
FileOutputStream fos = new FileOutputStream(fileName);
int res = IOUtils.copy(is, fos);
System.out.println("res : "+res);
is.close();
fos.flush();fos.close();
br.close();
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
Client Side Code
public class FileTransferClient {
public FileTransferClient() {
// TODO Auto-generated constructor stub
}
/**
* #param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
try {
Socket socket = new Socket("172.16.4.23",5000);
File file = new File("/Users/Guest/Desktop/DQM.txt");
OutputStream outputStream = socket.getOutputStream();
PrintWriter out = new PrintWriter(outputStream);
out.println("file-transfer");
out.flush();
out.println(""+file.getName());
out.flush();
FileInputStream fis = new FileInputStream(file);
int res = IOUtils.copy(fis, outputStream);
out.flush();
outputStream.flush();
outputStream.close();
fis.close();
System.out.println("res : "+res);
socket.close();
} catch (UnknownHostException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
How to make this program to transfer files between system
I have tried with Windows (Server) & Mac OS X(Client) and Windows (Server) & LinuxMint(Client)
Note :
1. I want to send File Name followed by file content.
2. File content may be in any form (Text or Binary file)

You cannot mix test and binary in the same stream unless you really know what you are doing. In this case the BufferedReader assumes you will only use this reader from now on and it can read as much data as is available. This means it can read data you intended to be for the file.
I suggest you use DataInput/OutputStream, and only this. You can use writeUtf/readUTF for the text.
To write
Socket socket = new Socket("172.16.4.23",5000);
String pathname = "/Users/Guest/Desktop/DQM.txt";
DataOutputStream dos = new DataOutputStream(socket.getOutputStream());
outputStream.writeUTF(pathname);
FileInputStream fis = new FileInputStream(pathname);
int res = IOUtils.copy(fis, dos);
fis.close();
dos.close();
socket.close();
To read
DataInputStream dis = new DataInputStream(socket.getInputStream());
String fileName = dis.readUTF();
FileOutputStream fos = new FileOutputStream(fileName);
int res = IOUtils.copy(dis, fos);
fos.close();
socket.close();

Related

How to copy file in resource folder in java

Need a quick help. I am new to Java..In my project I have input & output folder in resources. Inside input folder I have a csv file. I need to move that file to output folder through java code. How to copy that input file to output directory. I have tried in google but not getting a working solution. My project structure is based on standard maven project.
I think there are at least four methods you can use to move your csv file to some other directory.
I assume that you already know the absolute directory path.
Method 1. The way of apache commons
You can use apache commons io library.
public static void moveWithApacheCommonsIO()
{
File sourceFile = new File("resource/AssetsImportCompleteSample.csv");
File destinationFile = new File("resource/aa/AssetsImportCompleteSample.csv");
try {
FileUtils.moveFile(sourceFile, destinationFile);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
Method 2. The way of java's NIO
You can also use nio (non-blocking io) in java
public static void moveWithFileNIO()
{
File sourceFile = new File("resource/AssetsImportCompleteSample.csv");
File destinationFile = new File("resource/aa/AssetsImportCompleteSample.csv");
FileInputStream inputStream = null;
FileOutputStream outputStream = null;
sourceFile.deleteOnExit();
try {
inputStream = new FileInputStream(sourceFile);
outputStream = new FileOutputStream(destinationFile);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
final FileChannel inChannel = inputStream.getChannel();
final FileChannel outChannel = outputStream.getChannel();
try {
inChannel.transferTo(0, inChannel.size(), outChannel);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
finally
{
try {
inChannel.close();
outChannel.close();
inputStream.close();
outputStream.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
Method 3. The traditional way of java's IO
You can use traditional method with file in and output stream in java.(Blocking IO)
public static void moveWithFileInOutStream()
{
File sourceFile = new File("resource/AssetsImportCompleteSample.csv");
File destinationFile = new File("resource/aa/AssetsImportCompleteSample.csv");
InputStream fin = null;
OutputStream fout = null;
sourceFile.deleteOnExit();
try {
fin = new BufferedInputStream(new FileInputStream(sourceFile));
fout = new BufferedOutputStream(new FileOutputStream(destinationFile));
byte[] readBytes = new byte[1024];
int readed = 0;
while((readed = fin.read(readBytes)) != -1)
{
fout.write(readBytes, 0, readed);
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
finally
{
try {
fin.close();
fout.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
Method 4. Using JNI(Java Native Interface)
Finally, you can use some function like mv or MovFile depending on your Operating system with JNI.
I think it is out of scope of this topic. you can google it or see JNA library to accomplish your task if you want.
Here are complete code for you.
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.nio.channels.FileChannel;
import org.apache.commons.io.FileUtils;
public class MovefileTest {
public static void moveWithApacheCommonsIO()
{
File sourceFile = new File("resource/AssetsImportCompleteSample.csv");
File destinationFile = new File("resource/aa/AssetsImportCompleteSample.csv");
try {
FileUtils.moveFile(sourceFile, destinationFile);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public static void moveWithFileInOutStream()
{
File sourceFile = new File("resource/AssetsImportCompleteSample.csv");
File destinationFile = new File("resource/aa/AssetsImportCompleteSample.csv");
InputStream fin = null;
OutputStream fout = null;
sourceFile.deleteOnExit();
try {
fin = new BufferedInputStream(new FileInputStream(sourceFile));
fout = new BufferedOutputStream(new FileOutputStream(destinationFile));
byte[] readBytes = new byte[1024];
int readed = 0;
while((readed = fin.read(readBytes)) != -1)
{
fout.write(readBytes, 0, readed);
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
finally
{
try {
fin.close();
fout.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
public static void moveWithFileNIO()
{
File sourceFile = new File("resource/AssetsImportCompleteSample.csv");
File destinationFile = new File("resource/aa/AssetsImportCompleteSample.csv");
FileInputStream inputStream = null;
FileOutputStream outputStream = null;
sourceFile.deleteOnExit();
try {
inputStream = new FileInputStream(sourceFile);
outputStream = new FileOutputStream(destinationFile);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
final FileChannel inChannel = inputStream.getChannel();
final FileChannel outChannel = outputStream.getChannel();
try {
inChannel.transferTo(0, inChannel.size(), outChannel);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
finally
{
try {
inChannel.close();
outChannel.close();
inputStream.close();
outputStream.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
public static void main(String[] args) {
//moveWithApacheCommonsIO();
//moveWithFileNIO();
moveWithFileInOutStream();
}
}
Regards,

Java client-server

This problem is bugging me for over a day now and I cannot find a fix for it.I am writing a chat application in Java.The problem is that the server cannot send messages to the clients,but can only receive it.Here are my classes:
Server class:
public class Server implements Runnable {
static InetAddress address;
static ArrayList<Integer> clients=new ArrayList<Integer>();
static ArrayList<Socket> socs=new ArrayList<>();
static String message="";
static DataOutputStream toClient;
static ServerSocket socket;
static Socket socketNew;
static boolean running=false;
public Server(InetAddress address){
this.address=address;
}
public static void main(String[] args) throws IOException
{
socket=new ServerSocket(8000);
System.out.println("Server started on port 8000");
running=true;
while(true)
{
socketNew=socket.accept();
socs.add(socketNew);
address=socketNew.getInetAddress();
System.out.println("connected to client at address: "+address);
Server server=new Server(address);
new Thread(server).start();
}
}
public void run() {
{
try {
BufferedReader br = new BufferedReader(new InputStreamReader(socketNew.getInputStream()));
String message=br.readLine();
System.out.println(message);
for(Socket s:socs) //sending the above msg. to all clients
{
OutputStream os=os = s.getOutputStream();
PrintWriter pw = new PrintWriter(os, true);
pw.write(message);
pw.flush();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
private void message() {
}
}
Here is my client class' relevant functions:
private void receive_data()
{
BufferedReader br;
try {
br = new BufferedReader(new InputStreamReader(socket.getInputStream()));
String message=br.readLine();
console(message);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
private void send_data() {
OutputStream os;
try {
os = socket.getOutputStream();
PrintWriter pw = new PrintWriter(os, true);
pw.println(this.name+": "+textField.getText());
pw.flush();
textField.setText("");
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
Also,the server stop taking any messages from the client after the very first message.I thought that problem can be eliminated by enclosing the contents of the run() method in server class inside while loop.But it is throwing exceptions that way.Any solutions to the above problem?
public void run() {
try {
BufferedReader br = new BufferedReader(new InputStreamReader(socketNew.getInputStream()));
String message;
PrintWriter out;
while ((message = br.readLine()) != null) {
for (Socket s : socs) // sending the above msg. to all clients
{
out = new PrintWriter(s.getOutputStream(), true);
out.println(message);
}
}
} catch (IOException e) {
e.printStackTrace();
}
}
There you go. Tested it with a small client i quickly wrote myself and it works.
And you definitely should work on your code formatting. (mainly those scope brackets that are there for no reason.)

java.net.SocketException: Connection reset error

I am using socket in Java.
Client send a name and phone number.
then sever get client data and encrypt it.
however problem accrue.
java.net.SocketException: Connection reset
at java.net.SocketInputStream.read(SocketInputStream.java:168)
at java.io.DataInputStream.readFully(DataInputStream.java:178)
at java.io.DataInputStream.readUTF(DataInputStream.java:592)
at java.io.DataInputStream.readUTF(DataInputStream.java:547)
at chat.QrcodeServer.dataEnc(QrcodeServer.java:45)
at chat.QrcodeServer.main(QrcodeServer.java:25)
Server:
import java.io.*;
import java.net.*;
public class QrcodeServer{
public static void main (String[] args){
ServerSocket ss = null;
Socket client = null;
int port = 10000;
try {
ss = new ServerSocket(port);
System.out.println("Service is started in "+ port);
}catch (IOException ee){
ee.printStackTrace();
}
try{
while (true){
client = ss.accept();
System.out.println("Client Info:" + client);
dataEnc(client);
}
}catch(IOException ee){
ee.printStackTrace();
}
}
public static void dataEnc(Socket client){
// Get an input file handle from the socket and read the input
InputStream cin=null;
String data=null;
String password=null;
try {
//get client Data Stream
cin = client.getInputStream();
DataInputStream dis = new DataInputStream(cin);
//get data
data = new String (dis.readUTF());
password = new String(dis.readUTF());
System.out.println(data);
System.out.println(password);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
//To make password hash
String passwordTemp = Crypto.getPassword(password);
try {
//encrypt data through passwordTemp
byte[] cipher = Crypto.encrypt(data,passwordTemp);
//printout the cipher data
System.out.print("cipher: ");
for(int i=0; i<cipher.length;i++){
System.out.print(Integer.toHexString(0xff&cipher[i])+" ");
}
System.out.println();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
Client:
import java.io.*;
import java.net.*;
public class Client {
public static void main(String[] args) {
// TODO Auto-generated method stub
Socket server = null;
String ip = "ip addr";
int port = 10000;
try{
server = new Socket(ip, port);
System.out.println("server: "+ip + "and port is "+ port );
sendInfo(server);
}catch(IOException e){
e.printStackTrace();
}
}
public static void sendInfo (Socket soc){
// Get a communication stream associated with the socket
OutputStream cout;
try {
cout = soc.getOutputStream();
DataOutputStream dos = new DataOutputStream (cout);
String name="kevin";
String phone="123456780";
String password="password";
String data = name+phone;
// Send a data
dos.writeUTF(data);
dos.writeUTF(password);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
It works in localhost and local interior network.
but problem above accrue when client connected from internet.
What might be the problem?

tomcat servlet sessions get merged

I'm developing a server that should receive ,multiple files instantaneously and be able to save them to the local hard drive. After the file received the server should send a response to the client and confirm that the file passed. When i'm trying to send multiple files instantaneously the result is that 1 client received the answer of the second and vice versa.
Does any one have a clue what is the problem with this server?
Here is my servlet code:
protected void doPost(final HttpServletRequest request, final HttpServletResponse response) throws ServletException, IOException {
try {
request.setCharacterEncoding("UTF-8");
} catch (UnsupportedEncodingException e2) {
// TODO Auto-generated catch block
e2.printStackTrace();
}
response.setCharacterEncoding("UTF-8");
PrintWriter writer = null;
try {
writer = response.getWriter();
} catch (IOException e2) {
// TODO Auto-generated catch block
e2.printStackTrace();
}
try {
// get access to file that is uploaded from client
Part p1 = request.getPart("File");
InputStream is = p1.getInputStream();
// read filename which is sent as a part
Part p2 = request.getPart("MetaData");
Scanner s = new Scanner(p2.getInputStream());
String stringJson = s.nextLine(); // read filename from stream
s.close();
json = new JSONObject(stringJson);
fileName = new String(json.getString("FileName").getBytes("UTF-8"));
fileDirectory = BASE + request.getSession().getId();
File dir = new File(fileDirectory);
dir.mkdir();
// get filename to use on the server
String outputfile = BASE + dir.getName() + "/" + fileName; // get path on the server
FileOutputStream os = new FileOutputStream (outputfile);
// write bytes taken from uploaded file to target file
byte[] buffer = new byte[1024];
int ch = is.read(buffer);
final Object lock = new Object();
while (ch != -1) {
synchronized (lock) {
os.write(buffer);
ch = is.read(buffer);
}
}
os.close();
is.close();
}
catch(Exception ex) {
writer.println("Exception -->" + ex.getMessage());
}
finally {
try {
myRequest = request;
try {
printFile(request.getSession().getId(), writer);
} catch (IOException e) {
// TODO Auto-generated catch block
writer.println("Exception -->" + e.getMessage());
}
writer.close();
} catch (InterruptedException e) {
writer.println("Exception -->" + e.getMessage());
}
}
}
Thanks in advance :)

How to use HttpURLConnection to send serialized object to a Servlet from Java class?

I want to send a serialized object from a Java class to a servlet where the servlet should retrieve and save the object as a file. I'm aware that I have to use HttpURLConnection to make a POST request to a servlet, but I don't know whether the below code is correct.
private static HttpURLConnection urlCon;
private static ObjectOutputStream out;
public static void main(String[] args) {
Names names = new Names();
names.setName("ABC");
names.setPlace("Bangalore");
URL url;
try {
url = new URL("http://localhost:6080/HttpClientSerializable/HttpPostServlet");
try {
out = (ObjectOutputStream) urlCon.getOutputStream();
out.writeObject(names);
urlCon = (HttpURLConnection) url.openConnection();
urlCon.setRequestMethod("POST");
urlCon.setDoOutput(true);
out.close();
} catch (IOException e) {
e.printStackTrace();
}
} catch (MalformedURLException e1) {
e1.printStackTrace();
}
}
And in the servlet, I have the following code:
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
ObjectInputStream in = new ObjectInputStream(request.getInputStream());
try {
names = (Names) in.readObject();
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
in.close();
ObjectOutputStream out = new ObjectOutputStream(new FileOutputStream("C:/Documents and Settings/RAGASTH/Desktop/Names"));
out.writeObject(names);
out.close();
}
What should I do to make it work? Also, I want the servlet to send back the object it receives as response.
Any help would be appreciated. Thanks!
You would need to
Make sure the Names class implements java.io.Serializable marker interface.
Create an ObjectOutputStream from the servlet's outputstream as follows:
out = new ObjectOutputStream(urlCon.getOutputStream());
On the receiver side, once you read the object from the servlet's inputstream and persist in the file, write it back to the response's output stream as follows:
out = new ObjectOutputStream(response.getOutputStream());
out.writeObject(names);
out.close();
On the sender's side:
Names names = new Names();
names.setName("ABC");
names.setPlace("Bangalore");
URL url;
try {
url = new URL("http://localhost:6080/HttpClientSerializable/HttpPostServlet");
urlCon = (HttpURLConnection) url.openConnection();
urlCon.setDoOutput(true); // to be able to write.
urlCon.setDoInput(true); // to be able to read.
out = new ObjectOutputStream(urlCon.getOutputStream());
out.writeObject(names);
out.close();
ObjectInputStream ois = new ObjectInputStream(urlCon.getInputStream());
names = (Names) ois.readObject();
ois.close();
} catch (IOException e) {
e.printStackTrace();
}
catch (MalformedURLException e1) {
e1.printStackTrace();
}
On the receiver's side:
ObjectInputStream in = new ObjectInputStream(request.getInputStream());
try {
names = (Names) in.readObject();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
in.close();
ObjectOutputStream out = new ObjectOutputStream(
new FileOutputStream("C:/Documents and Settings/RAGASTH/Desktop/Names"));
out.writeObject(names);
out.close();
ObjectOutputStream oos = new ObjectOutputStream(response.getOutputStream());
oos.writeObject(names);
oos.close();

Categories