Java : Writing console output to file, Not working - java

I have written an app for port scanning and I want to write my console output to a file but a little problem occurred. "PrintStream" is not writing all console output to the file. For instance: code within try block which shows opened ports in the console does not write anything to the file, but dead hosts in catch block are written.
My code:
public class start {
public static void main(String[] args) throws IOException{
for (int i = 5935; i < 10000; i++){
new test(i);
}
PrintStream printStream = new PrintStream(new FileOutputStream("E:\\ports.txt"));
System.setOut(printStream);
printStream.flush();
}
}
class test implements Runnable{
static String host = "localhost";
int t;
Thread y;
public test(int t2){
t = t2;
y = new Thread(this);
y.start();
}
public void run() {
try {
Socket socket = new Socket(host, t);
System.out.println("Port is alive - " + t);
} catch (IOException e){
System.out.println("Port is dead... - " + t);
}
}
}

Close socket
Use Executor Service
Set output stream before writing output
Wait for all jobs to be ready
Flush output when ready
Close printStream
Results in:
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.PrintStream;
import java.net.Socket;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;
public class start
{
public static void main(String[] args) throws Exception {
try (PrintStream printStream = new PrintStream(new FileOutputStream("E:\\ports.txt"))) {
System.setOut(printStream);
ExecutorService pool = Executors.newCachedThreadPool();
for (int i = 5935; i < 10000; i++) {
final int port = i;
pool.execute(() -> {
try (Socket socket = new Socket("localhost", port)) {
System.out.println("Port is alive - " + port);
}
catch (IOException e) {
System.out.println("Port is dead... - " + port);
}
});
}
pool.awaitTermination(100, TimeUnit.SECONDS);
printStream.flush();
}
}
}

You have a few issues directly related to the issue at hand.
You set the output AFTER you have started the threads so where the output goes is almost random.
You don't wait for the threads to finish, so the application "just ends" at a random point.
You don't flush the output.
Updated code:
class StartPortTester {
public static void main(String[] args) throws IOException, InterruptedException {
// Set up the stream BEFORE starting threads
// This should be in a try-with-resources, or the close done in a finally block.
PrintStream printStream = new PrintStream(new FileOutputStream("ports.txt"));
System.setOut(printStream);
// Start the threads!
List<PortTester> testers = new LinkedList<>();
for (int i = 5935; i < 10000; i++){
testers.add(new PortTester(i));
}
// Wait for the threads to end
for(PortTester t : testers ) {
t.y.join();
}
// Flush (write to disk) and close.
printStream.flush();
printStream.close();;
}
}
class PortTester implements Runnable{
static String host = "localhost";
int t;
Thread y;
public PortTester(int t2){
t = t2;
y = new Thread(this);
y.start();
}
public void run() {
try {
// You should close this either in the finally block or using a try-with-resource.
Socket socket = new Socket(host, t);
System.out.println("Port is alive - " + t);
} catch (IOException e){
System.out.println("Port is dead... - " + t);
}
}
}
This is not perfect as
it creates a ton of threads andit would be much better to use a thread pool.
It also waits forever for the thread to finish, you might want it to only wait x seconds before giving up.
Exceptions would cause the file to not be flushed & closed.
You mix up presentation with logic. I'd NOT write System.out in the PortTester, but create a data structure describing the ports statuses and then output that after (separate presentation from logic).
At the moment the ordering of the output is random (based on when the threads finish).

Related

Server Client Exception

I have a problem in running server-client program. When i run my server program , it keeps on running and never ends up. On other side, when i run my client program it throws an exception as shown below (my firewall is off).
The replies will be more than appreciated. Thanks
//Client Code
import java.io.*;
import java.net.*;
public class DailyAdviceClient
{
public void go()
{
try {
Socket s = new Socket("127.0.0.1", 4242);
InputStreamReader read = new InputStreamReader(s.getInputStream());
BufferedReader z = new BufferedReader(read);
String advice = z.readLine();
System.out.println("today you should" + advice);
z.close();
}
catch (IOException ex)
{
ex.printStackTrace();
}
}
public static void main(String[] args)
{
DailyAdviceClient x = new DailyAdviceClient();
x.go();
}
}
//Server Code
import java.io.*;
import java.net.*;
public class DailyAdvisor
{
String[] advicelist = { "take your time", "be patient",
"don't be diplomatic", " life is really short", "try to fix things" };
public void go()
{
try
{
ServerSocket s = new ServerSocket(4242);
while (true)
{
Socket m = s.accept();
PrintWriter writer = new PrintWriter(m.getOutputStream());
String advice = getAdvice();
writer.println(advice);
writer.close();
writer.flush();
System.out.println(advice);
}
} catch (IOException ex)
{
ex.printStackTrace();
}
}
private String getAdvice()
{
int random = (int) (Math.random() * advicelist.length);
return advicelist[random];
}
public static void main(String[] args)
{
DailyAdvisor x = new DailyAdvisor();
x.go();
}
}
The Server never ends up because you used a while(true) loop. It is necessary for your server to keep listening to new client connections through the accept() method.
About the exception, your code runs fine both locally and using a remote machine. Thus a network configuration error could be the cause and you must check if both server/client could see each other using the ping command. If this is the case, then check if the server is listening to the client using netstat.

stop thread with udp server

I've got an UDP server class which implements Runnable interface. I start it in the thread.
The problem is that I can't stop it. Even in Debug it stops on pt.join() method.
Here is my server class
import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.SocketException;
public class Network implements Runnable {
final int port = 6789;
DatagramSocket socket;
byte[] input = new byte[1024];
byte[] output = new byte[1024];
public Network() throws SocketException{
socket = new DatagramSocket(6789);
}
#Override
public void run() {
while(true){
DatagramPacket pack = new DatagramPacket(input,input.length);
try {
socket.receive(pack);
} catch (IOException e) {
e.printStackTrace();
}
input = pack.getData();
System.out.println(new String(input));
output = "Server answer".getBytes();
DatagramPacket sendpack = new DatagramPacket(output,output.length,pack.getAddress(),pack.getPort());
try {
socket.send(sendpack);
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
This is the main class
public class Main {
static Network network = null;
public static void main(String[] args) throws IOException{
network = new Network();
System.out.println("Try to start server");
Thread pt = new Thread(network);
pt.start();
pt.interrupt();
try {
pt.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("Stop server");
}
}
How to stop server?
java.net reads are non-interruptible. You would have to either close the DatagramSocket or have it read with a timeout (setSoTimeout()), and when you get the resulting SocketTimeoutException check the interrupt status: if set, exit the thread.
Calling interrupt doesn't actually stop the thread, it just sets a flag.
Inside your loop, check for isInterrupted(). e.g., a quick and dirty way would be change
while(true)
to
while (!Thread.currentThread().isInterrupted())
But you should consult some more documentation if you get more serious about this project.
As mentioned by #EJP, if you are hanging in the Socket IO, you'll need to close the Socket or have a timeout.
In addition to what EJP said, you probably should have a local boolean called running (or whatever), and set it to true before you enter your while loop. Have your while loop be conditioned on this local boolean. And provide methods (stopServer() and isRunning()) to set and check the status of the boolean. You also might want to remove the try-catch from inside the while loop and put the entire while loop within a try-catch-finally and in the finally statement perform clean-up (set running=false; close the connection, etc)

How does a program run after main() exits?

I have written a program that uses the twitter stream to write tweets in Realtime to a File via a BufferedWriter.
But the bufferedWriter does not write the text until i call the close() method at the end of the main function.
Now, when i run the program, the file is closed at first and then the tweets start coming. How does this thing work after main exits???
Here is the Code:
package analytics;
import twitter4j.*;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.Arrays;
public final class Trial_Filters {
static String Tweet;
static FileWriter output;
static BufferedWriter writer;
public static void main(String[] args) throws TwitterException,IOException {
if (args.length < 1) {
System.out.println("Usage: java twitter4j.examples.PrintFilterStream [follow(comma separated numerical user ids)] [track(comma separated filter terms)]");
System.exit(-1);
}
output= new FileWriter("Log.txt");
writer=new BufferedWriter(output);
StatusListener listener = new StatusListener() {
public void onStatus(Status status) {
StringBuilder temp;
//System.out.print("<sta>"); // Start Status -- helps for parsing two lines tweet;<sta> and </sta> used as tweet delimiters
temp=new StringBuilder("<sta>");
if(status.isRetweet())
temp.append("%");//System.out.print("%"); // easier to identify ReTweets
//System.out.println("#" + status.getUser().getScreenName() + " - " + status.getText());
temp.append("#" + status.getUser().getScreenName() + " - " + status.getText());
//System.out.print("</sta>"); //End Status
temp.append("</sta>");
Tweet=temp.toString();
this.add_to_Log();
}
private void add_to_Log(){
// TODO Auto-generated method stub
try{
output= new FileWriter("Log.txt");
writer=new BufferedWriter(output);
writer.write(Tweet);
System.out.println(Tweet);
}
catch(Exception e)
{
System.out.println(e);
}
}
public void onDeletionNotice(StatusDeletionNotice statusDeletionNotice) {
System.out.println("Got a status deletion notice id:" + statusDeletionNotice.getStatusId());
}
public void onTrackLimitationNotice(int numberOfLimitedStatuses) {
System.out.println("Got track limitation notice:" + numberOfLimitedStatuses);
}
public void onScrubGeo(long userId, long upToStatusId) {
System.out.println("Got scrub_geo event userId:" + userId + " upToStatusId:" + upToStatusId);
}
public void onException(Exception ex) {
ex.printStackTrace();
}
};
TwitterStream twitterStream = new TwitterStreamFactory().getInstance();
twitterStream.addListener(listener);
ArrayList<Long> follow = new ArrayList<Long>();
ArrayList<String> track = new ArrayList<String>();
for (String arg : args) {
if (isNumericalArgument(arg)) {
for (String id : arg.split(",")) {
follow.add(Long.parseLong(id));
}
} else {
track.addAll(Arrays.asList(arg.split(",")));
}
}
long[] followArray = new long[follow.size()];
for (int i = 0; i < follow.size(); i++) {
followArray[i] = follow.get(i);
}
String[] trackArray = track.toArray(new String[track.size()]);
// filter() method internally creates a thread which manipulates TwitterStream and calls these adequate listener methods continuously.
twitterStream.filter(new FilterQuery(0, followArray, trackArray));
try{
System.out.println("bye");
writer.close();
}
catch(Exception e)
{
System.out.println(e);
}
}
private static boolean isNumericalArgument(String argument) {
String args[] = argument.split(",");
boolean isNumericalArgument = true;
for (String arg : args) {
try {
Integer.parseInt(arg);
} catch (NumberFormatException nfe) {
isNumericalArgument = false;
break;
}
}
return isNumericalArgument;
}
}
The virtual machine terminates all activity and exits after the last non-daemon thread ("User Thread") has terminated (or some thread invoked System.exit()). That last User thread doesn't have to be the main thread.
The tweets (packets) are sent to a local socket and the socket is only bound as long as the virtual machine is up and running (in case the socket hasn't been closed manually). So the feed may be sending but the computer won't accept the data and the tweet source will receive errors.
The TwitterStream Object will start a thread, and that thread will call back on the StatusListener. The program will run until there is a thread running, even if the main thread seems to have finished, it waits for all other threads to stop, before the main thread stops, and the program exits.
It does not matter if you close the writer or not on the end of main. The reference of the writer will be rewritten on each call to add_to_log. That means on each new status a new writer gets instantiated, writes out the message into the bufferedwriter.
The following two lines at the beginning of the code are irrelevant:
output= new FileWriter("Log.txt");
writer=new BufferedWriter(output);
However it would be better to call flush() or close() in add_to_log to make sure everything gets written to disk.
When you close a program with a bufferedWriter activated, the system triggers the buffered writer to flush its output to whatever endpoint it's hooked up to, be it a file or stdout. Over time, what could be happening, is that documents are arriving on the socket and getting placed into the bufferedwriter, but your the writer just stores them up because you haven't called flush() from the code or the writer threshold for doing a dump hasn't been crossed. When you call close, under the hood, it calls flush and forces the output to dump--even if the program is "closed".

Using Threads to Handle Sockets

I am working on a java program that is essentially a chat room. This is an assignment for class so no code please, I am just having some issues determining the most feasible way to handle what I need to do. I have a server program already setup for a single client using threads to get the data input stream and a thread to handle sending on the data output stream. What I need to do now is create a new thread for each incoming request.
My thought is to create a linked list to contain either the client sockets, or possibly the thread. Where I am stumbling is figuring out how to handle sending the messages out to all the clients. If I have a thread for each incoming message how can I then turn around and send that out to each client socket.
I'm thinking that if I had a linkedlist of the clientsockets I could then traverse the list and send it out to each one, but then I would have to create a dataoutputstream each time. Could I create a linkedlist of dataoutputstreams? Sorry if it sounds like I'm rambling but I don't want to just start coding this, it could get messy without a good plan. Thanks!
EDIT
I decided to post the code I have so far. I haven't had a chance to test it yet so any comments would be great. Thanks!
import java.io.BufferedReader;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.Socket;
import java.net.ServerSocket;
import java.util.LinkedList;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
public class prog4_server {
// A Queue of Strings used to hold out bound Messages
// It blocks till on is available
static BlockingQueue<String> outboundMessages = new LinkedBlockingQueue<String>();
// A linked list of data output streams
// to all the clients
static LinkedList<DataOutputStream> outputstreams;
// public variables to track the number of clients
// and the state of the server
static Boolean serverstate = true;
static int clients = 0;
public static void main(String[] args) throws IOException{
//create a server socket and a clientSocket
ServerSocket serverSocket = null;
try {
serverSocket = new ServerSocket(6789);
} catch (IOException e) {
System.out.println("Could not listen on port: 6789");
System.exit(-1);
}// try{...}catch(IOException e){...}
Socket clientSocket;
// start the output thread which waits for elements
// in the message queue
OutputThread out = new OutputThread();
out.start();
while(serverstate){
try {
// wait and accept a new client
// pass the socket to a new Input Thread
clientSocket = serverSocket.accept();
DataOutputStream ServerOut = new DataOutputStream(clientSocket.getOutputStream());
InputThread in = new InputThread(clientSocket, clients);
in.start();
outputstreams.add(ServerOut);
} catch (IOException e) {
System.out.println("Accept failed: 6789");
System.exit(-1);
}// try{...}catch{..}
// increment the number of clients and report
clients = clients++;
System.out.println("Client #" + clients + "Accepted");
}//while(serverstate){...
}//public static void main
public static class OutputThread extends Thread {
//OutputThread Class Constructor
OutputThread() {
}//OutputThread(...){...
public void run() {
//string variable to contain the message
String msg = null;
while(!this.interrupted()) {
try {
msg = outboundMessages.take();
for(int i=0;i<outputstreams.size();i++){
outputstreams.get(i).writeBytes(msg + '\n');
}// for(...){...
} catch (IOException e) {
System.out.println(e);
} catch (InterruptedException e){
System.out.println(e);
}//try{...}catch{...}
}//while(...){
}//public void run(){...
}// public OutputThread(){...
public static class InputThread extends Thread {
Boolean threadstate = true;
BufferedReader ServerIn;
String user;
int threadID;
//SocketThread Class Constructor
InputThread(Socket clientSocket, int ID) {
threadID = ID;
try{
ServerIn = new BufferedReader(
new InputStreamReader(clientSocket.getInputStream()));
user = ServerIn.readLine();
}
catch(IOException e){
System.out.println(e);
}
}// InputThread(...){...
public void run() {
String msg = null;
while (threadstate) {
try {
msg = ServerIn.readLine();
if(msg.equals("EXITEXIT")){
// if the client is exiting close the thread
// close the output stream with the same ID
// and decrement the number of clients
threadstate = false;
outputstreams.get(threadID).close();
outputstreams.remove(threadID);
clients = clients--;
if(clients == 0){
// if the number of clients has dropped to zero
// close the server
serverstate = false;
ServerIn.close();
}// if(clients == 0){...
}else{
// add a message to the message queue
outboundMessages.add(user + ": " + msg);
}//if..else...
} catch (IOException e) {
System.out.println(e);
}// try { ... } catch { ...}
}// while
}// public void run() { ...
}
public static class ServerThread extends Thread {
//public variable declaration
BufferedReader UserIn =
new BufferedReader(new InputStreamReader(System.in));
//OutputThread Class Constructor
ServerThread() {
}//OutputThread(...){...
public void run() {
//string variable to contain the message
String msg = null;
try {
//while loop will continue until
//exit command is received
//then send the exit command to all clients
msg = UserIn.readLine();
while (!msg.equals("EXITEXIT")) {
System.out.println("Enter Message: ");
msg = UserIn.readLine();
}//while(...){
outboundMessages.add(msg);
serverstate = false;
UserIn.close();
} catch (IOException e) {
System.out.println(e);
}//try{...}catch{...}
}//public void run(){...
}// public serverThread(){...
}// public class prog4_server
I have solved this problem in the past by defining a "MessageHandler" class per client connection, responsible for inbound / outbound message traffic. Internally the handler uses a BlockingQueue implementation onto which outbound messages are placed (by internal worker threads). The I/O sender thread continually attempts to read from the queue (blocking if required) and sends each message retrieved to the client.
Here's some skeleton example code (untested):
/**
* Our Message definition. A message is capable of writing itself to
* a DataOutputStream.
*/
public interface Message {
void writeTo(DataOutputStream daos) throws IOException;
}
/**
* Handler definition. The handler contains two threads: One for sending
* and one for receiving messages. It is initialised with an open socket.
*/
public class MessageHandler {
private final DataOutputStream daos;
private final DataInputStream dais;
private final Thread sender;
private final Thread receiver;
private final BlockingQueue<Message> outboundMessages = new LinkedBlockingQueue<Message>();
public MessageHandler(Socket skt) throws IOException {
this.daos = new DataOutputStream(skt.getOutputStream());
this.dais = new DataInputStream(skt.getInputStream());
// Create sender and receiver threads responsible for performing the I/O.
this.sender = new Thread(new Runnable() {
public void run() {
while (!Thread.interrupted()) {
Message msg = outboundMessages.take(); // Will block until a message is available.
try {
msg.writeTo(daos);
} catch(IOException ex) {
// TODO: Handle exception
}
}
}
}, String.format("SenderThread-%s", skt.getRemoteSocketAddress()));
this.receiver = new Thread(new Runnable() {
public void run() {
// TODO: Read from DataInputStream and create inbound message.
}
}, String.format("ReceiverThread-%s", skt.getRemoteSocketAddress()));
sender.start();
receiver.start();
}
/**
* Submits a message to the outbound queue, ready for sending.
*/
public void sendOutboundMessage(Message msg) {
outboundMessages.add(msg);
}
public void destroy() {
// TODO: Interrupt and join with threads. Close streams and socket.
}
}
Note that Nikolai is correct in that blocking I/O using 1 (or 2) threads per connection is not a scalable solution and typically applications might be written using Java NIO to get round this. However, in reality unless you're writing an enterprise server which thousands of clients connect to simultaneously then this isn't really an issue. Writing bug-free scalable applications using Java NIO is difficult and certainly not something I'd recommend.

Java sockets with thread execution

i have coded a socket listener that should listen on port 80 and 81 and when data arrive on these ports execute operations on these data. I want this listener to concurrently listen on both these ports and hav coded in the following way.
import java.net.*;
import java.io.*;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
public class MultipleSocketServer implements Runnable {
private int a;
private ServerSocket connection;
private String TimeStamp;
private int ID;
public static void main(String[] args){
// System.out.print("ip");
// String gh="12345";
//System.out.println(gh.substring(1,3));
int port = 80;
int port1 = 81;
int count = 0;
double a=234.52121;
//System.out.println(bf3.toString());
try{
ServerSocket socket1 = new ServerSocket(port);
ServerSocket socket2=new ServerSocket(port1);
System.out.println("MultipleSocketServer Initialized");
Runnable runnable = new MultipleSocketServer(socket1, ++count);
Runnable run = new MultipleSocketServer(socket2, ++count);
Thread thread = new Thread(runnable);
Thread thread1 = new Thread(run);
while (true) {
//Socket connection = socket1.accept();
thread.start();
thread1.start();
}
}
catch (Exception e) {}
}
MultipleSocketServer(ServerSocket s, int i) {
this.connection = s;
this.ID = i;
}
public void run() {
while(true){
try {
Socket incoming=connection.accept();
BufferedInputStream is = new BufferedInputStream(incoming.getInputStream());
int character;
while((character = is.read())!=-1) {
.
.
do the input data handling here
.
.
}
}
catch(Exception e){}
}
}
}
But for some reason this does not seem to show the threaded/conncurrent behaviour.
I am testing this code using Hyperterminal, and every time i disconnect from hyperterminal, the program execution stops and "Socket is closed" exception is raised.
Any pointers would be of great help
Cheers
You're starting threads in an endless loop.
while (true) {
//Socket connection = socket1.accept();
thread.start();
thread1.start();
}
I think though, that this is handled (ignored) in
} catch (Exception e) {}
However, I suspect that the problem you describe is in in the handling code you didn't include. One pretty obvious idea: you don't call connection.close() instead of incoming.close(), do you?

Categories

Resources