add debug logging

This commit is contained in:
Arnaud Vergnet 2020-12-16 10:46:48 +01:00
parent e7dd395d29
commit 312bbaa5a6
7 changed files with 63 additions and 43 deletions

View file

@ -1,8 +1,8 @@
package fr.insa.clavardator; package fr.insa.clavardator;
import fr.insa.clavardator.ui.MainController; import fr.insa.clavardator.ui.MainController;
import fr.insa.clavardator.users.User;
import fr.insa.clavardator.users.UserList; import fr.insa.clavardator.users.UserList;
import fr.insa.clavardator.util.Log;
import javafx.application.Application; import javafx.application.Application;
import javafx.fxml.FXMLLoader; import javafx.fxml.FXMLLoader;
import javafx.scene.Parent; import javafx.scene.Parent;
@ -21,6 +21,8 @@ public class MainApp extends Application {
@Override @Override
public void start(Stage stage) throws Exception { public void start(Stage stage) throws Exception {
Log.verboseLevel = 4;
Log.v("START", "Application started");
final FXMLLoader mainLoader = new FXMLLoader(getClass().getResource("ui/scene.fxml")); final FXMLLoader mainLoader = new FXMLLoader(getClass().getResource("ui/scene.fxml"));
final Parent content = mainLoader.load(); final Parent content = mainLoader.load();
@ -35,7 +37,7 @@ public class MainApp extends Application {
stage.setTitle("Clavardator"); stage.setTitle("Clavardator");
stage.setMinHeight(640); stage.setMinHeight(640);
stage.setMinWidth(800); stage.setMinWidth(800);
stage.setMaximized(true); // stage.setMaximized(true);
stage.show(); stage.show();
} }

View file

@ -1,6 +1,7 @@
package fr.insa.clavardator.network; package fr.insa.clavardator.network;
import fr.insa.clavardator.util.ErrorCallback; import fr.insa.clavardator.util.ErrorCallback;
import fr.insa.clavardator.util.Log;
import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Nullable;
import java.io.IOException; import java.io.IOException;
@ -28,6 +29,7 @@ public class NetDiscoverer {
* @param errorCallback function to call on error * @param errorCallback function to call on error
*/ */
public void discoverActiveUsers(String broadcastMessage, ResponseReceivedCallback callback, ErrorCallback errorCallback) { public void discoverActiveUsers(String broadcastMessage, ResponseReceivedCallback callback, ErrorCallback errorCallback) {
Log.v(this.getClass().getSimpleName(), "Starting user discovery");
if (responseListener != null) if (responseListener != null)
responseListener.stopListening(); responseListener.stopListening();
responseListener = new ResponseListener(callback, errorCallback); responseListener = new ResponseListener(callback, errorCallback);
@ -44,6 +46,7 @@ public class NetDiscoverer {
* @param errorCallback The function to call on error * @param errorCallback The function to call on error
*/ */
public void startDiscoveryListening(String responseMessage, @Nullable BroadcastReceivedCallback onBroadcastReceived, @Nullable ErrorCallback errorCallback) { public void startDiscoveryListening(String responseMessage, @Nullable BroadcastReceivedCallback onBroadcastReceived, @Nullable ErrorCallback errorCallback) {
Log.v(this.getClass().getSimpleName(), "Starting broadcast listening");
if (broadcastListener != null) if (broadcastListener != null)
broadcastListener.stopListening(); broadcastListener.stopListening();
@ -94,10 +97,10 @@ public class NetDiscoverer {
DatagramSocket broadcastSocket = new DatagramSocket(); DatagramSocket broadcastSocket = new DatagramSocket();
broadcastSocket.setBroadcast(true); broadcastSocket.setBroadcast(true);
broadcastSocket.send(new DatagramPacket(buf, buf.length, broadcastAddr, DISCOVERY_PORT)); broadcastSocket.send(new DatagramPacket(buf, buf.length, broadcastAddr, DISCOVERY_PORT));
// System.out.println("Broadcast sent with address " + broadcastAddr.toString()); Log.v(this.getClass().getSimpleName(), "Broadcast sent on address " + broadcastAddr.toString());
} }
} catch (IOException e) { } catch (IOException e) {
Log.e(this.getClass().getSimpleName(), "Error sending broadcast", e);
errorCallback.onError(e); errorCallback.onError(e);
} }
} }
@ -110,7 +113,7 @@ public class NetDiscoverer {
private boolean shouldStop = false; private boolean shouldStop = false;
/** /**
* Constructs a thread that sends a broadcast over the network, using all available interfaces * Constructs a thread that receives broadcast messages over the network, on all available interfaces
* *
* @param callback The function to call on success * @param callback The function to call on success
* @param errorCallback The function to call on error * @param errorCallback The function to call on error
@ -133,11 +136,12 @@ public class NetDiscoverer {
DatagramPacket receivedPacket = new DatagramPacket(buffer, BROADCAST_BUFFER_SIZE); DatagramPacket receivedPacket = new DatagramPacket(buffer, BROADCAST_BUFFER_SIZE);
socket.receive(receivedPacket); socket.receive(receivedPacket);
// System.out.println("broadcast received from " + receivedPacket.getAddress().toString()); Log.v(this.getClass().getSimpleName(), "Broadcast received from ip " + receivedPacket.getAddress().toString());
callback.onBroadcastReceived(receivedPacket.getAddress(), new String(receivedPacket.getData())); callback.onBroadcastReceived(receivedPacket.getAddress(), new String(receivedPacket.getData()));
} }
} catch (IOException e) { } catch (IOException e) {
if (!shouldStop) { if (!shouldStop) {
Log.e(this.getClass().getSimpleName(), "Error receiving broadcast message", e);
errorCallback.onError(e); errorCallback.onError(e);
} }
} }
@ -155,7 +159,7 @@ public class NetDiscoverer {
private final ErrorCallback errorCallback; private final ErrorCallback errorCallback;
/** /**
* Constructs a thread that sends a UDP response * Constructs a thread that sends a UDP response to a broadcast
* *
* @param address The address of the remote host * @param address The address of the remote host
* @param message The message to send * @param message The message to send
@ -173,8 +177,9 @@ public class NetDiscoverer {
try { try {
DatagramSocket responseSocket = new DatagramSocket(); DatagramSocket responseSocket = new DatagramSocket();
responseSocket.send(new DatagramPacket(buf, buf.length, address, RESPONSE_PORT)); responseSocket.send(new DatagramPacket(buf, buf.length, address, RESPONSE_PORT));
// System.out.println("Response sent to " + address.toString()); Log.v(this.getClass().getSimpleName(), "Broadcast response sent to ip " + address.toString());
} catch (IOException e) { } catch (IOException e) {
Log.e(this.getClass().getSimpleName(), "Error sending broadcast response to " + address.toString(), e);
errorCallback.onError(e); errorCallback.onError(e);
} }
} }
@ -187,7 +192,7 @@ public class NetDiscoverer {
private boolean shouldStop = false; private boolean shouldStop = false;
/** /**
* Constructs a thread that receives all UDP responses, until stopDiscovery() is called * Constructs a thread that receives all UDP responses, until stopListening() is called
* *
* @param callback The function to call on success * @param callback The function to call on success
* @param errorCallback The function to call on error * @param errorCallback The function to call on error
@ -209,11 +214,12 @@ public class NetDiscoverer {
byte[] buffer = new byte[RESPONSE_BUFFER_SIZE]; byte[] buffer = new byte[RESPONSE_BUFFER_SIZE];
DatagramPacket receivedPacket = new DatagramPacket(buffer, RESPONSE_BUFFER_SIZE); DatagramPacket receivedPacket = new DatagramPacket(buffer, RESPONSE_BUFFER_SIZE);
socket.receive(receivedPacket); socket.receive(receivedPacket);
// System.out.println("response received from " + receivedPacket.getAddress().toString()); Log.v(this.getClass().getSimpleName(), "Broadcast response received from ip " + receivedPacket.getAddress().toString());
callback.onResponseReceived(receivedPacket.getAddress(), new String(receivedPacket.getData())); callback.onResponseReceived(receivedPacket.getAddress(), new String(receivedPacket.getData()));
} }
} catch (IOException e) { } catch (IOException e) {
if (!shouldStop) { if (!shouldStop) {
Log.e(this.getClass().getSimpleName(), "Error receiving broadcast response", e);
errorCallback.onError(e); errorCallback.onError(e);
} }
} }

View file

@ -64,7 +64,7 @@ public class PeerConnection {
} }
/** /**
* Subscibe to all incoming messages from the peer * Subscribe to the first incoming message from the peer
* *
* @param callback The function to call when a message is received * @param callback The function to call when a message is received
* @param errorCallback The function to call on error * @param errorCallback The function to call on error
@ -75,7 +75,7 @@ public class PeerConnection {
} }
/** /**
* Closes the socket, and silently cancel all running send and receive operations. * Closes the socket, and silently cancels all running send and receive operations.
*/ */
public void close() { public void close() {
shouldStop = true; shouldStop = true;
@ -87,6 +87,10 @@ public class PeerConnection {
} }
} }
/**
* Checks if the current connection is open
* @return True if the socket isstill open
*/
public boolean isOpen() { public boolean isOpen() {
return socket != null && socket.isConnected() && !socket.isClosed(); return socket != null && socket.isConnected() && !socket.isClosed();
} }

View file

@ -8,6 +8,7 @@ import fr.insa.clavardator.ui.dialogs.SnackbarController;
import fr.insa.clavardator.ui.users.UserListController; import fr.insa.clavardator.ui.users.UserListController;
import fr.insa.clavardator.users.CurrentUser; import fr.insa.clavardator.users.CurrentUser;
import fr.insa.clavardator.users.UserList; import fr.insa.clavardator.users.UserList;
import fr.insa.clavardator.util.Log;
import javafx.application.Platform; import javafx.application.Platform;
import javafx.fxml.FXML; import javafx.fxml.FXML;
import javafx.fxml.FXMLLoader; import javafx.fxml.FXMLLoader;
@ -90,9 +91,10 @@ public class MainController implements Initializable {
} }
private void discoverActiveUsers() { private void discoverActiveUsers() {
if (userList != null) if (userList != null) {
userList.discoverActiveUsers((e) -> CurrentUser.getInstance().setState(CurrentUser.State.INVALID)); userList.discoverActiveUsers((e) -> CurrentUser.getInstance().setState(CurrentUser.State.INVALID));
} }
}
private void startChat() { private void startChat() {
discoverActiveUsers(); discoverActiveUsers();
@ -124,7 +126,7 @@ public class MainController implements Initializable {
try { try {
currentUser.init(); currentUser.init();
System.out.println(currentUser.getId()); Log.v("INIT", "Current user: " + currentUser.getUsername() + " / " + currentUser.getId());
} catch (SocketException e) { } catch (SocketException e) {
showError(); showError();
} }

View file

@ -4,6 +4,7 @@ import fr.insa.clavardator.chat.ChatHistory;
import fr.insa.clavardator.chat.Message; import fr.insa.clavardator.chat.Message;
import fr.insa.clavardator.network.PeerConnection; import fr.insa.clavardator.network.PeerConnection;
import fr.insa.clavardator.util.ErrorCallback; import fr.insa.clavardator.util.ErrorCallback;
import fr.insa.clavardator.util.Log;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import java.io.EOFException; import java.io.EOFException;
@ -11,11 +12,10 @@ import java.net.InetAddress;
import java.net.Socket; import java.net.Socket;
public class PeerUser extends User implements Comparable<PeerUser> { public class PeerUser extends User implements Comparable<PeerUser> {
protected transient ChatHistory history;
private State state = State.DISCONNECTED; private State state = State.DISCONNECTED;
private transient PeerConnection connection; private transient PeerConnection connection;
protected transient ChatHistory history;
public PeerUser(int id, String username) { public PeerUser(int id, String username) {
super(id, username); super(id, username);
history = new ChatHistory(this); history = new ChatHistory(this);
@ -37,12 +37,14 @@ public class PeerUser extends User implements Comparable<PeerUser> {
if (connection != null && connection.isOpen()) { if (connection != null && connection.isOpen()) {
connection.close(); connection.close();
} }
Log.v(this.getClass().getSimpleName(), "Creating new TCP connection with " + id);
// Connect to the peer // Connect to the peer
setState(State.CONNECTING); setState(State.CONNECTING);
connection = new PeerConnection(ipAddr, (thisConnection) -> { connection = new PeerConnection(
init(thisConnection, callback, errorCallback); ipAddr,
}, e -> { (thisConnection) -> init(thisConnection, callback, errorCallback),
e -> {
Log.e(this.getClass().getSimpleName(), "Could not create TCP connection with " + id, e);
disconnect(); disconnect();
errorCallback.onError(e); errorCallback.onError(e);
}); });
@ -101,16 +103,19 @@ public class PeerUser extends User implements Comparable<PeerUser> {
private void subscribeToMessages(ErrorCallback errorCallback) { private void subscribeToMessages(ErrorCallback errorCallback) {
connection.receive( connection.receive(
msg -> { msg -> {
Log.v(this.getClass().getSimpleName(), "Received message from " + id);
if (msg.getClass().isInstance(UserInformation.class)) { if (msg.getClass().isInstance(UserInformation.class)) {
assert ((UserInformation) msg).id == getId(); assert ((UserInformation) msg).id == getId();
Log.v(this.getClass().getSimpleName(), "Message username: " + ((UserInformation) msg).getUsername());
setUsername(((UserInformation) msg).getUsername()); setUsername(((UserInformation) msg).getUsername());
} else if (msg.getClass().isInstance(Message.class)) { } else if (msg.getClass().isInstance(Message.class)) {
assert ((Message) msg).getRecipient().id != id; assert ((Message) msg).getRecipient().id != id;
Log.v(this.getClass().getSimpleName(), "Message text: " + ((Message) msg).getText());
history.addMessage((Message) msg); history.addMessage((Message) msg);
} }
}, },
e -> { e -> {
Log.e(this.getClass().getSimpleName(), "Error receiving message from " + id, e);
if (e.getClass().isInstance(EOFException.class)) { if (e.getClass().isInstance(EOFException.class)) {
disconnect(); disconnect();
} else { } else {
@ -121,6 +126,7 @@ public class PeerUser extends User implements Comparable<PeerUser> {
public void disconnect() { public void disconnect() {
Log.v(this.getClass().getSimpleName(), "Disconnecting from user: " + id);
if (connection != null && connection.isOpen()) { if (connection != null && connection.isOpen()) {
connection.close(); connection.close();
connection = null; connection = null;
@ -138,25 +144,19 @@ public class PeerUser extends User implements Comparable<PeerUser> {
return history; return history;
} }
public State getState() {
return state;
}
private void setState(State state) { private void setState(State state) {
pcs.firePropertyChange("state", this.state, state); pcs.firePropertyChange("state", this.state, state);
this.state = state; this.state = state;
} }
public State getState() {
return state;
}
public boolean isActive() { public boolean isActive() {
return state == State.CONNECTED; return state == State.CONNECTED;
} }
enum State {
CONNECTING,
CONNECTED,
DISCONNECTED,
}
@Override @Override
public int compareTo(@NotNull PeerUser peerUser) { public int compareTo(@NotNull PeerUser peerUser) {
if (peerUser.isActive() && !this.isActive()) { if (peerUser.isActive() && !this.isActive()) {
@ -167,6 +167,12 @@ public class PeerUser extends User implements Comparable<PeerUser> {
return getUsername().compareTo(peerUser.getUsername()); return getUsername().compareTo(peerUser.getUsername());
} }
enum State {
CONNECTING,
CONNECTED,
DISCONNECTED,
}
public interface UserConnectedCallback { public interface UserConnectedCallback {
void onUserConnected(); void onUserConnected();
} }

View file

@ -8,7 +8,7 @@ import java.io.Serializable;
public class User implements Serializable { public class User implements Serializable {
private String username; private String username;
public int id; protected int id;
// Make this class observable // Make this class observable
protected final transient PropertyChangeSupport pcs = new PropertyChangeSupport(this); protected final transient PropertyChangeSupport pcs = new PropertyChangeSupport(this);

View file

@ -3,6 +3,7 @@ package fr.insa.clavardator.users;
import fr.insa.clavardator.db.DatabaseController; import fr.insa.clavardator.db.DatabaseController;
import fr.insa.clavardator.network.NetDiscoverer; import fr.insa.clavardator.network.NetDiscoverer;
import fr.insa.clavardator.util.ErrorCallback; import fr.insa.clavardator.util.ErrorCallback;
import fr.insa.clavardator.util.Log;
import java.net.InetAddress; import java.net.InetAddress;
import java.util.ArrayList; import java.util.ArrayList;
@ -33,33 +34,32 @@ public class UserList {
public void discoverActiveUsers(ErrorCallback errorCallback) { public void discoverActiveUsers(ErrorCallback errorCallback) {
netDiscoverer.discoverActiveUsers("CLAVARDATOR_BROADCAST", (ipAddr, data) -> { netDiscoverer.discoverActiveUsers("CLAVARDATOR_BROADCAST", (ipAddr, data) -> {
int id = getIdFromIp(ipAddr); int id = getIdFromIp(ipAddr);
Log.v(this.getClass().getSimpleName(), "Discovered new user: " + id);
// If already connected, do not modify // If already connected, do not modify
if (activeUsers.containsKey(id)) { if (activeUsers.containsKey(id)) {
return; return;
} }
PeerUser user = inactiveUsers.get(id); PeerUser user = inactiveUsers.get(id);
if (user == null) { if (user == null) {
// Username is set on TCP connection start
user = new PeerUser(id, ""); user = new PeerUser(id, "");
} }
PeerUser finalUser = user; PeerUser finalUser = user;
user.connect(ipAddr, () -> { user.connect(ipAddr, () -> notifyConnectionObservers(finalUser), errorCallback);
notifyConnectionObservers(finalUser);
}, errorCallback);
}, errorCallback); }, errorCallback);
} }
public void startDiscoveryListening() { public void startDiscoveryListening() {
netDiscoverer.startDiscoveryListening("", null, Throwable::printStackTrace); netDiscoverer.startDiscoveryListening(
"CLAVARDATOR_RESPONSE",
null,
Throwable::printStackTrace);
} }
private int getIdFromIp(InetAddress ipAddr) { private int getIdFromIp(InetAddress ipAddr) {
return ipAddr.hashCode(); return ipAddr.hashCode();
} }
public void addActiveUsersObserver(UserConnectionCallback connectionCallback, UserDisconnectionCallback disconnectionCallback) { public void addActiveUsersObserver(UserConnectionCallback connectionCallback, UserDisconnectionCallback disconnectionCallback) {
userConnectionObservers.add(connectionCallback); userConnectionObservers.add(connectionCallback);
userDisconnectionObservers.add(disconnectionCallback); userDisconnectionObservers.add(disconnectionCallback);