I am trying to write a test for the writeMessage() method. But I have no idea how to start, since I need to test an OutputStream. This should be something like a small chat. It should read a message from console, write it to the text file and than print all messages that have been written to the file.
This is for a university project.
import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.PrintStream;
public class ChatIntImplement implements ChatI {
public static String readMessage() throws IOException, NullPointerException{
InputStream is = System.in;
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String message = null;
try {
message = br.readLine();
}catch(IOException ex) {
System.err.println("couldn't write data (fatal)");
System.exit(0);
}
return message;
}
public static void messageToFile(String message) throws IOException {
try {
String filename = "savedMessage.txt";
OutputStream os = new FileOutputStream(filename, true);
PrintStream ps = new PrintStream(os);
ps.println(message);
}catch (FileNotFoundException ex) {
System.err.println("couldn't open file - fatal");
System.exit(0);
}
}
public static void showMessages() {
InputStream is = null;
try {
is = new FileInputStream("savedMessage.txt");
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String message;
while((message = br.readLine())!= null) {
System.out.println(message);
}
}catch(FileNotFoundException ex) {
System.err.println("couln't open file -fatal");
System.exit(0);
}catch(IOException e) {
System.err.println("couldn't read data (fatal)");
System.exit(0);
}
}
#Override
public void writeMessage(String message){
try {
messageToFile(message);
showMessages();
}catch (IOException e) {
System.err.println("couldn't write data (fatal");
System.exit(0);
}
}
#Override
public void exit() {
// TODO Auto-generated method stub
}
public static void main(String[] args) {
ChatIntImplement chat = new ChatIntImplement();
try {
String message = readMessage();
chat.writeMessage(message);
}catch (IOException e) {
System.err.println("couldn't write data (fatal");
System.exit(0);
}catch (NullPointerException npe) {
System.err.println("Du hast nichts eingegeben");
System.exit(0);
}
}
}
I think the problem you are having getting started is because of how you have structured your class. All of your methods are static, and each method's dependencies, such as the various input and output streams you are using, are created as needed inside each method. For instance, in your messageToFile(...) method:
OutputStream os = new FileOutputStream(filename, true);
A much better approach to your project would be design your class using a traditional object-oriented class design that makes use of a pattern called Dependency Injection
The idea here is that your class that implements your ChatI interface would use member-variables for your input and output streams and the other objects, which would be initialized in the constructor for the class. Then you could control, and most importantly, get access to those streams from within your unit tests - something like this perhaps:
#Test
public void givenAMessageString_When() {
String expectedInput="expectedString";
ByteArrayOutputStream baos = new ByteArrayOutputStream();
ChatIntImplement chat = new ChatIntImplement(baos);
...
chat.writeMessage(expectedInput);
string output = new String(baos.toByteArray());
assertThat(output).equals(expectedInput);
}
Related
What I wanna do is get the content of this URL :
https://www.aviationweather.gov/adds/dataserver_current/httpparam?dataSource=metars&requestType=retrieve&format=xml&stationString=CYQB&hoursBeforeNow=2
and copy it to a file so I can parse it and use the elements.
Here is what I have so far :
package test;
import java.io.*;
import java.net.*;
import org.apache.commons.io.FileUtils;
public class JavaGetUrl {
#SuppressWarnings("deprecation")
public static void main(String[] args) throws FileNotFoundException {
URL u;
InputStream is = null;
DataInputStream dis;
String s = null;
try {
u = new URL(
"https://www.aviationweather.gov/adds/dataserver_current/httpparam?dataSource=metars&requestType=retrieve&format=xml&stationString=CYQB&hoursBeforeNow=2");
is = u.openStream(); // throws an IOException
dis = new DataInputStream(new BufferedInputStream(is));
while ((s = dis.readLine()) != null) {
System.out.println(s);
FileUtils.writeStringToFile(new File("input.txt"), s);
}
} catch (MalformedURLException mue) {
System.out.println("Ouch - a MalformedURLException happened.");
mue.printStackTrace();
System.exit(1);
} catch (IOException ioe) {
System.out.println("Oops- an IOException happened.");
ioe.printStackTrace();
System.exit(1);
} finally {
try {
is.close();
} catch (IOException ioe) {
}
}
}
}
The problem is that the content of s does not show up in input.txt.
If I replace s by any other strings it works. So I guess it's a problem with the data of s. Is it because it's xml?
Thank you all for the help.
The file is probably getting over-written.
You should use "append" mode to get file appended with data(from readLine).
public static void writeStringToFile(File file,
String data,
boolean append)
as you are already using apaches commons-io, you can also simply use
FileUtils.copyURLToFile(URL, File)
see https://commons.apache.org/proper/commons-io/javadocs/api-2.4/org/apache/commons/io/FileUtils.html#copyURLToFile(java.net.URL,%20java.io.File)
I'm trying to develop a simple Java file transfer application using TCP.
My current server code is as follows:
package tcp.ftp;
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.ServerSocket;
import java.net.Socket;
public class FTPServer {
public static void main(String[] args) {
new FTPServer().go();
}
void go() {
try {
ServerSocket server = new ServerSocket(2015);
System.out.println("server is running ....!");
while (true) {
Socket socket = server.accept();
BufferedReader reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));
String file = reader.readLine();
System.out.println("file to be downloaded is : " + file);
BufferedInputStream bis = new BufferedInputStream(new FileInputStream(file));
BufferedOutputStream bos = new BufferedOutputStream(socket.getOutputStream());
while (true) {
int octet = bis.read();
if (octet == -1) {
break;
}
bos.write(octet);
}
bos.flush();
//bos.close();
}
} catch (IOException ex) {
System.out.println(ex.getMessage());
}
}
}
Using my current server code above, the downlloding does not work as expected. the above code sends part of the file to the client , not the entire file. Note that I used the flush method to flush the buffer. but when I replace the flush () method by the close () method, the file is fully sent to the client whithout any loss. Could anyone please explain this behavior!
UPDATE: Here is the code of my client:
package tcp.ftp;
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.PrintWriter;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;
/**
*
* #author aaa
*/
public class FTPClient {
public static void main(String[] args) {
String file = "JasperReports-Ultimate-Guide-3.pdf";
try {
InetAddress address = InetAddress.getLocalHost();
Socket socket = new Socket(address, 2015);
System.out.println("connection successfully established ....!");
PrintWriter pw = new PrintWriter(socket.getOutputStream());
pw.println(file);
pw.flush();
BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("copy" + file));
while (true) {
int octet = bis.read();
if (octet == -1) {
break;
}
bos.write(octet);
}
bos.flush();
System.out.println("file download is complete ...!");
} catch (UnknownHostException ex) {
System.out.println(ex.getMessage());
} catch (IOException ex) {
System.out.println(ex.getMessage());
}
}
}
Another behavior without the use of Socket. take the following code that copy a file from a source to a destination:
public class CopieFile {
static void fastCopy(String source, String destination) {
try {
FileInputStream fis = new FileInputStream(source);
BufferedInputStream bis = new BufferedInputStream(fis);
FileOutputStream fos = new FileOutputStream(destination);
BufferedOutputStream bos = new BufferedOutputStream(fos);
while (true) {
int octet = bis.read();
if (octet == -1) {
break;
}
bos.write(octet);
}
bos.flush();
} catch (FileNotFoundException ex) {
System.out.println(ex.getMessage());
} catch (IOException ex) {
System.out.println(ex.getMessage());
}
}
public static void main(String[] args) throws IOException {
String source = "...";
String destination = "...";
fastCopy(source, destination);
}// end main
}// end class
the above code to copy a file from one location to another without any loss. Note well that I did not close the stream.
If you never close the stream the client wil never get end of stream so it will never exit the read loop.
In any case the stream and the socket are about to go out of scope, so if you don't close them you have a resource leak.
I try to create my own class to output system out stream to console and to the file at the same time using BufferedStream. But data doesn't appear from the BufferedOutputStream. How should I fix this problem?
package com.library.stream;
import java.io.BufferedOutputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
public class DoubleEndedStream {
InputStream theInput;
OutputStream theOutput;
public static void main(String[] args) throws IOException, FileNotFoundException {
DoubleEndedStream sr = new DoubleEndedStream(System.in, System.out);
sr.doublingTheStream();
}
public DoubleEndedStream(InputStream in, OutputStream out) {
theInput = in;
theOutput = out;
}
public void doublingTheStream() throws IOException, FileNotFoundException {
try {
FileOutputStream fos = new FileOutputStream("C:\\log.txt");
BufferedOutputStream bout1 = new BufferedOutputStream(fos);
BufferedOutputStream bout2 = new BufferedOutputStream(theOutput);
try {
while (true) {
int datum = theInput.read();
if (datum == -1) break;
bout1.write(datum);
bout2.write(datum);
}
bout1.flush();
bout2.flush();
} catch (IOException e) {
System.err.println("Couldn't read from System.in!");
}
bout1.close();
bout2.close();
fos.close();
} catch (FileNotFoundException e) {
System.err.println("Couldn't find log.txt");
}
}
}
Since theInput is System.in, as long as you don't close it, (ctrl-d in unix), it will not return -1, but hang and wait for input. Since you perform flush() only when received -1, you never get to this point. Try flushing after the write() instead.
This is my Socket test program.
My problem is that when I execute the code below. After I call read() on Socket InputStream for first time, it block as expected.
But when loop go back to read() again, it never blocks on read() again? Thus it ends up with a tight and endless loop.
What should I do if I want to use separate thread to get server response? Is there any design pattern for this requirements?
package test.socket;
import java.io.BufferedReader;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.PrintWriter;
import java.net.Socket;
import java.net.UnknownHostException;
public class TestMario {
private InputStream in;
private OutputStream out;
public static void main(String[] args) throws Exception {
new TestMario().go();
}
public TestMario() {
try {
Socket echoSocket = new Socket("xxx.xxx.xxx.xxx", 1234);
in = echoSocket.getInputStream();
out = echoSocket.getOutputStream();
} catch (UnknownHostException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public void go() throws UnknownHostException, IOException {
Thread writer = new Thread(new Runnable() {
public void run() {
BufferedReader stdIn = new BufferedReader(new InputStreamReader(System.in));
PrintWriter writer = new PrintWriter(out);
String userInput;
try {
System.out.print("input your command:");
while ((userInput = stdIn.readLine()) != null) {
System.out.println("you type:" + userInput);
writer.print(userInput);
writer.flush();
}
} catch (IOException e) {
e.printStackTrace();
}
}
});
Thread reader = new Thread(new Runnable() {
StringBuffer sb = new StringBuffer();
public void run() {
while (true) {
System.out.println("waiting for server response...");
try {
ByteArrayOutputStream baos = new ByteArrayOutputStream();
byte[] content = new byte[512];
int bytesRead = -1;
while((bytesRead = in.read(content)) != -1) { // read() doesn't block anymore after first read
baos.write(content, 0, bytesRead);
} // while
System.out.println("got:" + new String(baos.toByteArray()));
}
catch (Exception e) {
e.printStackTrace();
}
}
}
});
writer.start();
reader.start();
System.out.println();
}
}
This means that it either returns -1 or throws IOException. You implemented 2 loops: the internal loop verifies that value returned by read and exits if value is -1. This is fine. However the outer loop while(true) makes you to enter the read again and again, so it is not blocked anymore because the end of stream is achieved.
EDIT: credits to #assylias that wrote comment that hints this.
I am trying to write a small Java application that will let me run a Bukkit server off-screen using the Java Process/ProcessBuilder API.
I am able to get the output from the server fine, but the server doesn't respond to commands written by the output stream returned by Process.getOutputStream() (chained to the process input stream).
I tried doing this with my own test code, and it worked. The separate process reading from System.in received the text written to the output stream.
Does Bukkit not listen to System.in or something?
If not, how can that be?
Any ideas?
try {
ProcessBuilder pb = new ProcessBuilder();
File dir = new File("C:/Users/Brian/Desktop/MC-Server/Bukkit-Testing");
pb.directory(dir);
pb.command(new String[] {"java", "-Xincgc", "-Xmx1G", "-jar", "craftbukkit-1.0.1-R1.jar"});
pb.redirectErrorStream(true);
final Process p = pb.start();
InputStream out = p.getInputStream();
BufferedReader r1 = new BufferedReader(new InputStreamReader(out));
String s = null;
new Thread(new Runnable() {
#Override
public void run() {
BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(p.getOutputStream()));
Scanner scan = new Scanner(System.in);
String input = null;
while((input=scan.nextLine()) != null) {
if(input.equals("exit")) {
p.destroy();
break;
}
try {
bw.write(input);
bw.flush();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}).start();
while((s=r1.readLine()) !=null)
System.out.println(s);
} catch (IOException e) {
e.printStackTrace();
}
I don't think Bukkit uses its System.in, so we have to make a workaround.
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.util.logging.Logger;
import org.bukkit.Bukkit;
import org.bukkit.plugin.java.JavaPlugin;
public class ConsolePlugin extends JavaPlugin {
public Logger log;
public void onEnable(){
log = this.getLogger();
log.info("BufferedReader has been enabled!");
new Thread(new Runnable(){
public void run(){
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
String line = null;
while (true){
try {
line=br.readLine();
} catch (Exception e) {e.printStackTrace();}
if (line!=null){
Bukkit.dispatchCommand(Bukkit.getConsoleSender(), line);
System.out.println(line);
}
}
}
}).start();
}
public void onDisable(){
log.info("BufferedReader has been disabled.");
}
}
To send commands:
bw.write(input);
bw.nextLine();
bw.flush();