package com.coder.client; import java.io.IOException; import java.util.Map; import java.util.logging.Level; import java.util.logging.Logger; import com.coder.client.Session; import com.coder.client.gui.editor.EditorWindow; import com.coder.client.gui.editor.EditorWindowListener; import com.coder.client.gui.login.LoginDialog; import com.coder.client.gui.login.LoginDialogListener; import com.coder.client.gui.selectProject.SelectProjectDialog; import com.coder.client.gui.selectProject.SelectProjectDialogListener; import com.coder.client.gui.selectServer.SelectServerDialog; import com.coder.client.gui.selectServer.SelectServerDialogListener; import com.coder.server.CoderServer; import com.coder.server.message.CoderMessage; import com.coder.server.message.ConfigData; import com.coder.server.message.ProjectListData; import com.coder.server.message.ProjectListReqMsg; import com.coder.server.message.ProjectRspMsg; import zutil.log.CompactLogFormatter; import zutil.log.LogUtil; import zutil.net.ssdp.SSDPClient; import zutil.net.ssdp.SSDPClient.SSDPServiceListener; import zutil.net.ssdp.StandardSSDPInfo; import javafx.application.Application; import javafx.application.Platform; import javafx.stage.Stage; public class CoderClient extends Application{ public static final Logger logger = LogUtil.getLogger(); private Session session; private Stage mainStage; //GUI elements private EditorWindow editorWindow; private LoginDialog loginDialog; private SelectProjectDialog selectProjectDialog; private SelectServerDialog selectServerDialog; //state variables private String serverURL = null; private int serverPort = CoderServer.SERVER_PORT; private String username = null; private char[] password = null; //should only be anything else than null if defined by program argument private String loginErrorMessage = ""; private String project = null; //services SSDPClient ssdpClient; public static void main(String[] args) { Application.launch(args); } @Override public void start(Stage mainStage) throws Exception { //setup logging LogUtil.setGlobalLevel(Level.INFO); LogUtil.setGlobalFormatter(new CompactLogFormatter()); //parse program arguments Map params = this.getParameters().getNamed(); for(String key : params.keySet()){ String value = params.get(key); if(key.equals("username")){ this.username = value; }else if(key.equals("password")){ this.password = value.toCharArray(); }else if(key.equals("url")){ this.serverURL = value; }else if(key.equals("port")){ try{ this.serverPort = Integer.parseInt(value); }catch(NumberFormatException e){ logger.warning("port argument to program is not of a integer type. using default port."); } }else if(key.equals("project")){ this.project = value; } } if(this.username == null){ //ignore the password if no username was set this.password = null; } //setup GUI elements this.mainStage = mainStage; mainStage.setTitle("CoderClient"); try{ setupSelectServerDialog(); setupLoginDialog(); setupSelectProjectDialog(); setupEditWindow(); }catch(IOException e){ logger.log(Level.SEVERE, "could not load all GUI elements", e); System.exit(1); } //setup SSDP client try{ setupSSDPClient(); }catch(IOException e){ logger.log(Level.SEVERE, "could not setup SSDP client", e); System.exit(1); } //start program logic selectServerDialog.showOnStage(mainStage); } private void setupSelectServerDialog() throws IOException{ this.selectServerDialog = new SelectServerDialog(); this.selectServerDialog.addSelectProjectDialogListener(new SelectServerDialogListener() { @Override public void willShow() { closeCurrentSession(); ssdpClient.clearServices(); selectServerDialog.clearServerList(); if(ssdpClient != null){ ssdpClient.requestService("coder:discover"); }else{ logger.severe("could not send a SSDP request since the client is not setup"); } selectServerDialog.setServerAddress(serverURL); selectServerDialog.setServerPort(serverPort); } @Override public void exit() { logger.info("terminating"); System.exit(0); } @Override public void connect(String address, int port) { //selectServerDialog.hide(); serverURL = address; serverPort = port; //connect session session = Session.setupConnection(serverURL, serverPort); if(session == null){ logger.warning("Could not setup a connection to " + serverURL + ":" + port); serverURL = null; serverPort = CoderServer.SERVER_PORT; selectServerDialog.showOnStage(mainStage); }else{ loginDialog.showOnStage(mainStage); } } }); } private void setupLoginDialog() throws IOException { this.loginDialog = new LoginDialog(); this.loginDialog.addLoginDialogListener(new LoginDialogListener(){ @Override public void willShow() { loginDialog.setUsername(username); loginDialog.setPassword(password); loginDialog.setErrorMessage(loginErrorMessage); } @Override public void cancel() { serverURL = null; serverPort = CoderServer.SERVER_PORT; selectServerDialog.showOnStage(mainStage); } @Override public void login(String uname, char[] paswd) { username = uname; password = paswd; //authenticate session boolean authenticated = session.authenticate(username, password); if(!authenticated){ logger.severe("Authentication failed: wrong username or password"); password = null; loginErrorMessage = "Wrong username or password"; selectServerDialog.showOnStage(mainStage); }else{ loginErrorMessage = ""; setupSessionListener(); //resister a message listener to the session session.start(); //start receiving traffic from the server selectProjectDialog.showOnStage(mainStage); } } private void setupSessionListener(){ session.addCoderMessageReceivedListener(new CoderMessageReceivedListener() { @Override public void projectListRspReceived(final Map projectListRsp) { Platform.runLater(new Runnable() { @Override public void run() { for(String projectName : projectListRsp.keySet()){ ProjectListData projectData = projectListRsp.get(projectName); selectProjectDialog.addProjectToList(projectName, projectData); } } }); } @Override public void projectRspReceived(ProjectRspMsg projectRspMsg) { // TODO Auto-generated method stub } @Override public void projectTypeRspReceived(Map projectTypeRsp) { // TODO Auto-generated method stub } }); } }); } private void setupSelectProjectDialog() throws IOException { this.selectProjectDialog = new SelectProjectDialog(); this.selectProjectDialog.addSelectProjectDialogListener(new SelectProjectDialogListener() { @Override public void willShow() { selectProjectDialog.clearProjectList(); if(project == null){ sendProjectListReq(); }else{ selectProjectDialog.setProject(project); } } @Override public void open(String selectedProjectName) { project = selectedProjectName; editorWindow.showOnStage(mainStage); } @Override public void newProject() { //TODO } @Override public void cancel() { serverURL = null; serverPort = CoderServer.SERVER_PORT; selectServerDialog.showOnStage(mainStage); } @Override public void refresh() { selectProjectDialog.clearProjectList(); sendProjectListReq(); } private void sendProjectListReq(){ //send a request for a new list of projects CoderMessage msg = new CoderMessage(); msg.ProjectListReq = new ProjectListReqMsg(); try { session.send(msg); } catch (IOException e) { logger.log(Level.SEVERE, "Unable to send ProjectListReqMsg", e); closeCurrentSession(); } } }); } private void setupEditWindow() throws IOException { this.editorWindow = new EditorWindow(); this.editorWindow.addEditorWindowListener(new EditorWindowListener() { @Override public void willShow() { //TODO } @Override public void compile() { //TODO } @Override public void run() { //TODO } }); } private void setupSSDPClient() throws IOException{ this.ssdpClient = new SSDPClient(); ssdpClient.setListener(new SSDPServiceListener() { @Override public void newService(final StandardSSDPInfo service) { if(selectServerDialog != null){ Platform.runLater(new Runnable() { @Override public void run() { String ip = service.getInetAddress().getHostAddress(); selectServerDialog.addServerToList(ip); } }); } } }); ssdpClient.start(); } private void closeCurrentSession(){ if(this.session != null){ logger.info("disconnecting from server"); session.close(); session = null; } } }