server

Clone or download

Documentation - 1

Modified Files

/*
Stream-Pi - Free & Open-Source Modular Cross-Platform Programmable Macropad
Copyright (C) 2019-2021 Debayan Sutradhar (rnayabed), Samuel Quiñones (SamuelQuinones)
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Written by : Debayan Sutradhar (rnayabed)
*/
package com.StreamPi.Server.Action;
package com.StreamPi.Server.Action;
import com.StreamPi.ActionAPI.Action.Action;
import com.StreamPi.ActionAPI.Action.Action;
import com.StreamPi.ActionAPI.Action.ActionType;
import com.StreamPi.ActionAPI.Action.ActionType;
import com.StreamPi.ActionAPI.Action.ServerConnection;
import com.StreamPi.ActionAPI.Action.ServerConnection;
import com.StreamPi.ActionAPI.Action.PropertySaver;
import com.StreamPi.ActionAPI.Action.PropertySaver;
import com.StreamPi.ActionAPI.ActionProperty.ClientProperties;
import com.StreamPi.ActionAPI.ActionProperty.Property.ControlType;
import com.StreamPi.ActionAPI.ActionProperty.Property.Property;
import com.StreamPi.ActionAPI.ActionProperty.Property.Property;
import com.StreamPi.ActionAPI.ActionProperty.Property.Type;
import com.StreamPi.ActionAPI.ActionProperty.Property.Type;
import com.StreamPi.ActionAPI.ActionProperty.ServerProperties;
import com.StreamPi.ActionAPI.ActionProperty.ServerProperties;
import com.StreamPi.ActionAPI.NormalAction.NormalAction;
import com.StreamPi.ActionAPI.NormalAction.NormalAction;
import com.StreamPi.Server.Controller.Controller;
import com.StreamPi.Util.Exception.MinorException;
import com.StreamPi.Util.Exception.MinorException;
import com.StreamPi.Util.Exception.SevereException;
import com.StreamPi.Util.Exception.SevereException;
import com.StreamPi.Util.Exception.StreamPiException;
import com.StreamPi.Util.Exception.StreamPiException;
import com.StreamPi.Util.Version.Version;
import com.StreamPi.Util.Version.Version;
import com.StreamPi.Util.XMLConfigHelper.XMLConfigHelper;
import com.StreamPi.Util.XMLConfigHelper.XMLConfigHelper;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.transform.Result;
import javax.xml.transform.Result;
import javax.xml.transform.Source;
import javax.xml.transform.Source;
import javax.xml.transform.Transformer;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import javax.xml.transform.stream.StreamResult;
import javafx.scene.image.ImageView;
import org.w3c.dom.NodeList;
import org.w3c.dom.NodeList;
import org.kordamp.ikonli.javafx.FontIcon;
import org.w3c.dom.Document;
import org.w3c.dom.Document;
import org.w3c.dom.Node;
import org.w3c.dom.Node;
import java.io.File;
import java.io.File;
import java.lang.module.*;
import java.lang.module.*;
import java.nio.file.Path;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashMap;
import java.util.List;
import java.util.List;
import java.util.ServiceLoader;
import java.util.ServiceLoader;
import java.util.logging.Level;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.logging.Logger;
import java.util.stream.Collectors;
import java.util.stream.Collectors;
import org.w3c.dom.Element;
import org.w3c.dom.Element;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.transform.Transformer;
public class NormalActionPlugins
public class NormalActionPlugins
{
{
private static NormalActionPlugins instance = null;
private static NormalActionPlugins instance = null;
private final Logger logger;
private final Logger logger;
private File configFile;
private File configFile;
private Document document;
private Document document;
private static String pluginsLocation = null;
private static String pluginsLocation = null;
/**
* Singleton class instance getter. Creates new one, when asked for the first time
*
* @return returns instance of NormalActionPlugins (one and only, always)
*/
public static synchronized NormalActionPlugins getInstance()
public static synchronized NormalActionPlugins getInstance()
{
{
if(instance == null)
if(instance == null)
{
{
instance = new NormalActionPlugins();
instance = new NormalActionPlugins();
}
}
return instance;
return instance;
}
}
/**
* Sets the folder location where the plugin JARs and their dependencies are stored
*
* @param location Folder location
*/
public static void setPluginsLocation(String location)
public static void setPluginsLocation(String location)
{
{
pluginsLocation = location;
pluginsLocation = location;
}
}
/**
* Private constructor
*/
private NormalActionPlugins()
private NormalActionPlugins()
{
{
logger = Logger.getLogger(NormalActionPlugins.class.getName());
logger = Logger.getLogger(NormalActionPlugins.class.getName());
normalPluginsHashmap = new HashMap<>();
normalPluginsHashmap = new HashMap<>();
}
}
/**
* init Method
*/
public void init() throws SevereException, MinorException
public void init() throws SevereException, MinorException
{
{
registerPlugins();
registerPlugins();
initPlugins();
initPlugins();
}
}
/**
* Used to fetch list of all external Plugins
*
* @return List of plugins
*/
public List<NormalAction> getPlugins()
public List<NormalAction> getPlugins()
{
{
return normalPlugins;
return normalPlugins;
}
}
/**
* Returns a plugin by its module name
*
* @param name Module Name
* @return The plugin. If not found, then null is returned
*/
public NormalAction getPluginByModuleName(String name)
public NormalAction getPluginByModuleName(String name)
{
{
logger.info("Plugin being requested : "+name);
logger.info("Plugin being requested : "+name);
Integer index = normalPluginsHashmap.getOrDefault(name, -1);
Integer index = normalPluginsHashmap.getOrDefault(name, -1);
if(index != -1)
if(index != -1)
{
{
return normalPlugins.get(index);
return normalPlugins.get(index);
}
}
return null;
return null;
}
}
private List<NormalAction> normalPlugins = null;
private List<NormalAction> normalPlugins = null;
HashMap<String, Integer> normalPluginsHashmap;
HashMap<String, Integer> normalPluginsHashmap;
/**
* Used to register plugins from plugin location
*/
public void registerPlugins() throws SevereException, MinorException
public void registerPlugins() throws SevereException, MinorException
{
{
logger.info("Registering external plugins from "+pluginsLocation+" ...");
logger.info("Registering external plugins from "+pluginsLocation+" ...");
try
try
{
{
configFile = new File(pluginsLocation+"/config.xml");
configFile = new File(pluginsLocation+"/config.xml");
DocumentBuilderFactory docFactory = DocumentBuilderFactory.newInstance();
DocumentBuilderFactory docFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder docBuilder = docFactory.newDocumentBuilder();
DocumentBuilder docBuilder = docFactory.newDocumentBuilder();
document = docBuilder.parse(configFile);
document = docBuilder.parse(configFile);
}
}
catch (Exception e)
catch (Exception e)
{
{
e.printStackTrace();
e.printStackTrace();
throw new SevereException("Plugins","Error reading plugins config.xml. Cannot continue.");
throw new SevereException("Plugins","Error reading plugins config.xml. Cannot continue.");
}
}
ArrayList<NormalAction> errorModules = new ArrayList<>();
ArrayList<NormalAction> errorModules = new ArrayList<>();
ArrayList<String> errorModuleError = new ArrayList<>();
ArrayList<String> errorModuleError = new ArrayList<>();
ArrayList<Action> pluginsConfigs = new ArrayList<>();
ArrayList<Action> pluginsConfigs = new ArrayList<>();
NodeList actionsNode = document.getElementsByTagName("actions").item(0).getChildNodes();
NodeList actionsNode = document.getElementsByTagName("actions").item(0).getChildNodes();
for(int i =0;i<actionsNode.getLength();i++)
for(int i =0;i<actionsNode.getLength();i++)
{
{
Node eachActionNode = actionsNode.item(i);
Node eachActionNode = actionsNode.item(i);
if(eachActionNode.getNodeType() != Node.ELEMENT_NODE)
if(eachActionNode.getNodeType() != Node.ELEMENT_NODE)
continue;
continue;
if(!eachActionNode.getNodeName().equals("action"))
if(!eachActionNode.getNodeName().equals("action"))
continue;
continue;
Element eachActionElement = (Element) eachActionNode;
Element eachActionElement = (Element) eachActionNode;
String name="";
String name;
Version version;
Version version;
try
try
{
{
name = XMLConfigHelper.getStringProperty(eachActionElement, "module-name");
name = XMLConfigHelper.getStringProperty(eachActionElement, "module-name");
version = new Version(XMLConfigHelper.getStringProperty(eachActionElement, "version"));
version = new Version(XMLConfigHelper.getStringProperty(eachActionElement, "version"));
}
}
catch (Exception e)
catch (Exception e)
{
{
logger.log(Level.WARNING, "Skipping configuration because invalid ...");
logger.log(Level.WARNING, "Skipping configuration because invalid ...");
e.printStackTrace();
e.printStackTrace();
continue;
continue;
}
}
ServerProperties serverProperties = new ServerProperties();
ServerProperties serverProperties = new ServerProperties();
NodeList serverPropertiesNodeList = eachActionElement.getElementsByTagName("properties").item(0).getChildNodes();
NodeList serverPropertiesNodeList = eachActionElement.getElementsByTagName("properties").item(0).getChildNodes();
for(int j = 0;j<serverPropertiesNodeList.getLength();j++)
for(int j = 0;j<serverPropertiesNodeList.getLength();j++)
{
{
Node eachPropertyNode = serverPropertiesNodeList.item(j);
Node eachPropertyNode = serverPropertiesNodeList.item(j);
if(eachPropertyNode.getNodeType() != Node.ELEMENT_NODE)
if(eachPropertyNode.getNodeType() != Node.ELEMENT_NODE)
continue;
continue;
if(!eachPropertyNode.getNodeName().equals("property"))
if(!eachPropertyNode.getNodeName().equals("property"))
continue;
continue;
Element eachPropertyElement = (Element) eachPropertyNode;
Element eachPropertyElement = (Element) eachPropertyNode;
try
try
{
{
Property property = new Property(XMLConfigHelper.getStringProperty(eachPropertyElement, "name"), Type.STRING);
Property property = new Property(XMLConfigHelper.getStringProperty(eachPropertyElement, "name"), Type.STRING);
property.setRawValue(XMLConfigHelper.getStringProperty(eachPropertyElement, "value"));
property.setRawValue(XMLConfigHelper.getStringProperty(eachPropertyElement, "value"));
serverProperties.addProperty(property);
serverProperties.addProperty(property);
}
}
catch (Exception e)
catch (Exception e)
{
{
logger.log(Level.WARNING, "Skipping property because invalid ...");
logger.log(Level.WARNING, "Skipping property because invalid ...");
e.printStackTrace();
e.printStackTrace();
}
}
}
}
Action action = new Action(ActionType.NORMAL);
Action action = new Action(ActionType.NORMAL);
action.setModuleName(name);
action.setModuleName(name);
action.setVersion(version);
action.setVersion(version);
action.getServerProperties().set(serverProperties);
action.getServerProperties().set(serverProperties);
pluginsConfigs.add(action);
pluginsConfigs.add(action);
}
}
logger.info("Size : "+pluginsConfigs.size());
logger.info("Size : "+pluginsConfigs.size());
Path pluginsDir = Paths.get(pluginsLocation); // Directory with plugins JARs
Path pluginsDir = Paths.get(pluginsLocation); // Directory with plugins JARs
try
try
{
{
// Search for plugins in the plugins directory
// Search for plugins in the plugins directory
ModuleFinder pluginsFinder = ModuleFinder.of(pluginsDir);
ModuleFinder pluginsFinder = ModuleFinder.of(pluginsDir);
// Find all names of all found plugin modules
// Find all names of all found plugin modules
List<String> p = pluginsFinder
List<String> p = pluginsFinder
.findAll()
.findAll()
.stream()
.stream()
.map(ModuleReference::descriptor)
.map(ModuleReference::descriptor)
.map(ModuleDescriptor::name)
.map(ModuleDescriptor::name)
.collect(Collectors.toList());
.collect(Collectors.toList());
// Create configuration that will resolve plugin modules
// Create configuration that will resolve plugin modules
// (verify that the graph of modules is correct)
// (verify that the graph of modules is correct)
Configuration pluginsConfiguration = ModuleLayer
Configuration pluginsConfiguration = ModuleLayer
.boot()
.boot()
.configuration()
.configuration()
.resolve(pluginsFinder, ModuleFinder.of(), p);
.resolve(pluginsFinder, ModuleFinder.of(), p);
// Create a module layer for plugins
// Create a module layer for plugins
ModuleLayer layer = ModuleLayer
ModuleLayer layer = ModuleLayer
.boot()
.boot()
.defineModulesWithOneLoader(pluginsConfiguration, ClassLoader.getSystemClassLoader());
.defineModulesWithOneLoader(pluginsConfiguration, ClassLoader.getSystemClassLoader());
logger.info("Loading plugins from jar ...");
logger.info("Loading plugins from jar ...");
// Now you can use the new module layer to find service implementations in it
// Now you can use the new module layer to find service implementations in it
normalPlugins = ServiceLoader
normalPlugins = ServiceLoader
.load(layer, NormalAction.class).stream()
.load(layer, NormalAction.class).stream()
.map(ServiceLoader.Provider::get)
.map(ServiceLoader.Provider::get)
.collect(Collectors.toList());
.collect(Collectors.toList());
logger.info("...Done!");
logger.info("...Done!");
}
}
catch (Exception e)
catch (Exception e)
{
{
e.printStackTrace();
e.printStackTrace();
throw new MinorException("Error", "Error loading modules\n"+e.getMessage()+"\nPlease fix the errors. Other plugins wont be loaded.");
throw new MinorException("Error", "Error loading modules\n"+e.getMessage()+"\nPlease fix the errors. Other plugins wont be loaded.");
}
}
sortedPlugins = new HashMap<>();
sortedPlugins = new HashMap<>();
for (NormalAction eachPlugin : normalPlugins) {
for (NormalAction eachPlugin : normalPlugins)
try {
{
try
{
eachPlugin.setPropertySaver(propertySaver);
eachPlugin.setPropertySaver(propertySaver);
eachPlugin.setServerConnection(serverConnection);
eachPlugin.setServerConnection(serverConnection);
eachPlugin.initProperties();
eachPlugin.initProperties();
Action foundAction = null;
Action foundAction = null;
for (Action action : pluginsConfigs) {
for (Action action : pluginsConfigs) {
if (action.getModuleName().equals(eachPlugin.getModuleName())
if (action.getModuleName().equals(eachPlugin.getModuleName())
&& action.getVersion().isEqual(eachPlugin.getVersion())) {
&& action.getVersion().isEqual(eachPlugin.getVersion())) {
foundAction = action;
foundAction = action;
List<Property> eachPluginStoredProperties = action.getServerProperties().get();
List<Property> eachPluginStoredProperties = action.getServerProperties().get();
List<Property> eachPluginCodeProperties = eachPlugin.getServerProperties().get();
List<Property> eachPluginCodeProperties = eachPlugin.getServerProperties().get();
for (int i =0;i< eachPluginCodeProperties.size(); i++) {
for (int i =0;i< eachPluginCodeProperties.size(); i++) {
Property eachPluginCodeProperty = eachPluginCodeProperties.get(i);
Property eachPluginCodeProperty = eachPluginCodeProperties.get(i);
Property foundProp = null;
Property foundProp = null;
for (Property eachPluginStoredProperty : eachPluginStoredProperties) {
for (Property eachPluginStoredProperty : eachPluginStoredProperties) {
if (eachPluginCodeProperty.getName().equals(eachPluginStoredProperty.getName())) {
if (eachPluginCodeProperty.getName().equals(eachPluginStoredProperty.getName())) {
eachPluginCodeProperty.setRawValue(eachPluginStoredProperty.getRawValue());
eachPluginCodeProperty.setRawValue(eachPluginStoredProperty.getRawValue());
foundProp = eachPluginStoredProperty;
foundProp = eachPluginStoredProperty;
}
}
}
}
eachPluginCodeProperties.set(i, eachPluginCodeProperty);
eachPluginCodeProperties.set(i, eachPluginCodeProperty);
if (foundProp != null) {
if (foundProp != null) {
eachPluginStoredProperties.remove(foundProp);
eachPluginStoredProperties.remove(foundProp);
}
}
}
}
eachPlugin.getServerProperties().set(eachPluginCodeProperties);
eachPlugin.getServerProperties().set(eachPluginCodeProperties);
break;
break;
}
}
}
}
if (foundAction != null)
if (foundAction != null)
pluginsConfigs.remove(foundAction);
pluginsConfigs.remove(foundAction);
else
else
{
{
List<Property> eachPluginStoredProperties = eachPlugin.getServerProperties().get();
List<Property> eachPluginStoredProperties = eachPlugin.getServerProperties().get();
for(Property property :eachPluginStoredProperties)
for(Property property :eachPluginStoredProperties)
{
{
if(property.getType() == Type.STRING || property.getType() == Type.INTEGER || property.getType() == Type.DOUBLE)
if(property.getType() == Type.STRING || property.getType() == Type.INTEGER || property.getType() == Type.DOUBLE)
property.setRawValue(property.getDefaultRawValue());
property.setRawValue(property.getDefaultRawValue());
}
}
}
}
if (!sortedPlugins.containsKey(eachPlugin.getCategory())) {
if (!sortedPlugins.containsKey(eachPlugin.getCategory())) {
ArrayList<NormalAction> actions = new ArrayList<>();
ArrayList<NormalAction> actions = new ArrayList<>();
sortedPlugins.put(eachPlugin.getCategory(), actions);
sortedPlugins.put(eachPlugin.getCategory(), actions);
}
}
sortedPlugins.get(eachPlugin.getCategory()).add(eachPlugin);
sortedPlugins.get(eachPlugin.getCategory()).add(eachPlugin);
/*logger.debug("-----Custom Plugin Debug-----" +
}
"\nAction Type : " + eachPlugin.getActionType() +
catch (Exception e)
"\nName : " + eachPlugin.getName() +
{
"\nFull Module Name : " + eachPlugin.getModuleName() +
"\nAuthor : " + eachPlugin.getAuthor() +
"\nCategory : " + eachPlugin.getCategory() +
"\nRepo : " + eachPlugin.getRepo() +
"\nVersion : " + eachPlugin.getVersion().getText() +
"\n---------------------------");*/
} catch (Exception e) {
e.printStackTrace();
e.printStackTrace();
errorModules.add(eachPlugin);
errorModules.add(eachPlugin);
errorModuleError.add(e.getMessage());
errorModuleError.add(e.getMessage());
}
}
}
}
try {
try {
saveServerSettings();
saveServerSettings();
} catch (MinorException e) {
} catch (MinorException e) {
e.printStackTrace();
e.printStackTrace();
}
}
logger.log(Level.INFO, "All plugins registered!");
logger.log(Level.INFO, "All plugins registered!");
if(errorModules.size() > 0)
if(errorModules.size() > 0)
{
{
StringBuilder errors = new StringBuilder("The following action modules could not be loaded:");
StringBuilder errors = new StringBuilder("The following action modules could not be loaded:");
for(int i = 0; i<errorModules.size(); i++)
for(int i = 0; i<errorModules.size(); i++)
{
{
normalPlugins.remove(errorModules.get(i));
normalPlugins.remove(errorModules.get(i));
errors.append("\n * ").append(errorModules.get(i).getModuleName()).append("\n(")
errors.append("\n * ").append(errorModules.get(i).getModuleName()).append("\n(")
.append(errorModuleError.get(i)).append(")");
.append(errorModuleError.get(i)).append(")");
}
}
throw new MinorException("Plugins", errors.toString());
throw new MinorException("Plugins", errors.toString());
}
}
for(int i = 0;i<normalPlugins.size();i++)
for(int i = 0;i<normalPlugins.size();i++)
{
{
normalPluginsHashmap.put(normalPlugins.get(i).getModuleName(), i);
normalPluginsHashmap.put(normalPlugins.get(i).getModuleName(), i);
}
}
}
}
/**
* Used to init plugins
*/
public void initPlugins() throws MinorException
public void initPlugins() throws MinorException
{
{
StringBuilder errors = new StringBuilder("There were errors registering the following plugins. As a result, they have been omitted : ");
StringBuilder errors = new StringBuilder("There were errors registering the following plugins. As a result, they have been omitted : ");
boolean isError = false;
boolean isError = false;
for(NormalAction eachPlugin : normalPlugins)
for(NormalAction eachPlugin : normalPlugins)
{
{
try
try
{
{
eachPlugin.initAction();
eachPlugin.initAction();
}
}
catch (Exception e)
catch (Exception e)
{
{
e.printStackTrace();
e.printStackTrace();
isError = true;
isError = true;
errors.append("\n* ")
errors.append("\n* ")
.append(eachPlugin.getName())
.append(eachPlugin.getName())
.append(" - ")
.append(" - ")
.append(eachPlugin.getModuleName())
.append(eachPlugin.getModuleName())
.append("\n");
.append("\n");
if(e instanceof StreamPiException)
if(e instanceof StreamPiException)
errors.append(((MinorException) e).getShortMessage());
errors.append(((MinorException) e).getShortMessage());
errors.append("\n");
errors.append("\n");
}
}
}
}
if(isError)
if(isError)
{
{
throw new MinorException("Plugin init error", errors.toString());
throw new MinorException("Plugin init error", errors.toString());
}
}
}
}
HashMap<String, ArrayList<NormalAction>> sortedPlugins;
HashMap<String, ArrayList<NormalAction>> sortedPlugins;
/**
* Gets list of sorted plugins
*
* @return Hashmap with category key, and list of plugins of each category
*/
public HashMap<String, ArrayList<NormalAction>> getSortedPlugins()
public HashMap<String, ArrayList<NormalAction>> getSortedPlugins()
{
{
return sortedPlugins;
return sortedPlugins;
}
}
/**
* @return Gets actions element from the config.xml in plugins folder
*/
private Element getActionsElement()
private Element getActionsElement()
{
{
return (Element) document.getElementsByTagName("actions").item(0);
return (Element) document.getElementsByTagName("actions").item(0);
}
}
/**
* Saves ServerProperties of every plugin in config.xml in plugins folder
*
* @throws MinorException Thrown when failed to save settings
*/
public void saveServerSettings() throws MinorException
public void saveServerSettings() throws MinorException
{
{
XMLConfigHelper.removeChilds(getActionsElement());
XMLConfigHelper.removeChilds(getActionsElement());
for(NormalAction normalAction : normalPlugins)
for(NormalAction normalAction : normalPlugins)
{
{
Element actionElement = document.createElement("action");
Element actionElement = document.createElement("action");
getActionsElement().appendChild(actionElement);
getActionsElement().appendChild(actionElement);
Element moduleNameElement = document.createElement("module-name");
Element moduleNameElement = document.createElement("module-name");
moduleNameElement.setTextContent(normalAction.getModuleName());
moduleNameElement.setTextContent(normalAction.getModuleName());
actionElement.appendChild(moduleNameElement);
actionElement.appendChild(moduleNameElement);
Element versionElement = document.createElement("version");
Element versionElement = document.createElement("version");
versionElement.setTextContent(normalAction.getVersion().getText());
versionElement.setTextContent(normalAction.getVersion().getText());
actionElement.appendChild(versionElement);
actionElement.appendChild(versionElement);
Element propertiesElement = document.createElement("properties");
Element propertiesElement = document.createElement("properties");
actionElement.appendChild(propertiesElement);
actionElement.appendChild(propertiesElement);
for(String key : normalAction.getServerProperties().getNames())
for(String key : normalAction.getServerProperties().getNames())
{
{
for(Property eachProperty : normalAction.getServerProperties().getMultipleProperties(key))
for(Property eachProperty : normalAction.getServerProperties().getMultipleProperties(key))
{
{
Element propertyElement = document.createElement("property");
Element propertyElement = document.createElement("property");
propertiesElement.appendChild(propertyElement);
propertiesElement.appendChild(propertyElement);
Element nameElement = document.createElement("name");
Element nameElement = document.createElement("name");
nameElement.setTextContent(eachProperty.getName());
nameElement.setTextContent(eachProperty.getName());
propertyElement.appendChild(nameElement);
propertyElement.appendChild(nameElement);
Element valueElement = document.createElement("value");
Element valueElement = document.createElement("value");
valueElement.setTextContent(eachProperty.getRawValue());
valueElement.setTextContent(eachProperty.getRawValue());
propertyElement.appendChild(valueElement);
propertyElement.appendChild(valueElement);
}
}
}
}
}
}
save();
save();
}
}
private PropertySaver propertySaver = null;
private PropertySaver propertySaver = null;
/**
* Set PropertySaver class
* @param propertySaver instance of PropertySaver
*/
public void setPropertySaver(PropertySaver propertySaver)
public void setPropertySaver(PropertySaver propertySaver)
{
{
this.propertySaver = propertySaver;
this.propertySaver = propertySaver;
}
}
private ServerConnection serverConnection = null;
private ServerConnection serverConnection = null;
/**
* Set setServerConnection class
* @param serverConnection instance of ServerConnection
*/
public void setServerConnection(ServerConnection serverConnection)
public void setServerConnection(ServerConnection serverConnection)
{
{
this.serverConnection = serverConnection;
this.serverConnection = serverConnection;
}
}
/**
* Get plugin from index from list
*
* @param index of plugin
* @return found plugin
*/
public NormalAction getActionFromIndex(int index)
public NormalAction getActionFromIndex(int index)
{
{
return normalPlugins.get(index);
return normalPlugins.get(index);
}
}
/**
* Calls onShutDown method in every plugin
*/
public void shutDownActions()
public void shutDownActions()
{
{
if(normalPlugins != null)
if(normalPlugins != null)
{
{
for(NormalAction eachPlugin : normalPlugins)
for(NormalAction eachPlugin : normalPlugins)
{
{
try
try
{
{
eachPlugin.onShutDown();
eachPlugin.onShutDown();
}
}
catch (Exception e)
catch (Exception e)
{
{
e.printStackTrace();
e.printStackTrace();
}
}
}
}
normalPlugins.clear();
normalPlugins.clear();
}
}
}
}
/**
* Saves all Server Properties of each Plugin in config.xml in Plugins folder
* @throws MinorException thrown when failed to save
*/
public void save() throws MinorException
public void save() throws MinorException
{
{
try
try
{
{
Transformer transformer = TransformerFactory.newInstance().newTransformer();
Transformer transformer = TransformerFactory.newInstance().newTransformer();
Result output = new StreamResult(configFile);
Result output = new StreamResult(configFile);
Source input = new DOMSource(document);
Source input = new DOMSource(document);
transformer.transform(input, output);
transformer.transform(input, output);
}
}
catch (Exception e)
catch (Exception e)
{
{
throw new MinorException("Config", "unable to save server plugins settings");
throw new MinorException("Config", "unable to save server plugins settings");
}
}
}
}
}
}
/*
Stream-Pi - Free & Open-Source Modular Cross-Platform Programmable Macropad
Copyright (C) 2019-2021 Debayan Sutradhar (rnayabed), Samuel Quiñones (SamuelQuinones)
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Written by : Debayan Sutradhar (rnayabed)
*/
package com.StreamPi.Server.Client;
package com.StreamPi.Server.Client;
import com.StreamPi.Server.Connection.ClientConnection;
import com.StreamPi.ThemeAPI.Theme;
import com.StreamPi.Util.Exception.MinorException;
import com.StreamPi.Util.Platform.Platform;
import com.StreamPi.Util.Platform.Platform;
import com.StreamPi.Util.Platform.ReleaseStatus;
import com.StreamPi.Util.Platform.ReleaseStatus;
import com.StreamPi.Util.Version.Version;
import com.StreamPi.Util.Version.Version;
import javafx.geometry.Dimension2D;
import java.net.SocketAddress;
import java.net.SocketAddress;
import java.util.ArrayList;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.List;
public class Client {
public class Client {
private String nickName;
private String nickName;
private final SocketAddress remoteSocketAddress;
private final SocketAddress remoteSocketAddress;
private final Platform platform;
private final Platform platform;
private ClientConnection connectionHandler;
private final Version version;
private final Version version;
private final Version commStandardVersion;
private final Version commStandardVersion;
private final Version themeAPIVersion;
private final Version themeAPIVersion;
private final ReleaseStatus releaseStatus;
private final ReleaseStatus releaseStatus;
private double startupDisplayHeight, startupDisplayWidth;
private double startupDisplayHeight, startupDisplayWidth;
private final HashMap<String,ClientProfile> profiles;
private final HashMap<String,ClientProfile> profiles;
private final HashMap<String,ClientTheme> themes;
private final HashMap<String,ClientTheme> themes;
private String defaultProfileID;
private String defaultProfileID;
private String defaultThemeFullName;
private String defaultThemeFullName;
private int totalNoOfProfiles;
public Client(Version version, ReleaseStatus releaseStatus, Version commStandardVersion, Version themeAPIVersion, String nickName, Platform platform, SocketAddress remoteSocketAddress)
public Client(Version version, ReleaseStatus releaseStatus, Version commStandardVersion, Version themeAPIVersion, String nickName, Platform platform, SocketAddress remoteSocketAddress)
{
{
this.version = version;
this.version = version;
this.releaseStatus = releaseStatus;
this.releaseStatus = releaseStatus;
this.commStandardVersion = commStandardVersion;
this.commStandardVersion = commStandardVersion;
this.themeAPIVersion = themeAPIVersion;
this.themeAPIVersion = themeAPIVersion;
this.nickName = nickName;
this.nickName = nickName;
this.remoteSocketAddress = remoteSocketAddress;
this.remoteSocketAddress = remoteSocketAddress;
this.platform = platform;
this.platform = platform;
this.profiles = new HashMap<>();
this.profiles = new HashMap<>();
this.themes = new HashMap<>();
this.themes = new HashMap<>();
}
}
public ReleaseStatus getReleaseStatus() {
public ReleaseStatus getReleaseStatus() {
return releaseStatus;
return releaseStatus;
}
}
public void setDefaultThemeFullName(String defaultThemeFullName) {
public void setDefaultThemeFullName(String defaultThemeFullName) {
this.defaultThemeFullName = defaultThemeFullName;
this.defaultThemeFullName = defaultThemeFullName;
}
}
public String getDefaultThemeFullName() {
public String getDefaultThemeFullName() {
return defaultThemeFullName;
return defaultThemeFullName;
}
}
public void setTotalNoOfProfiles(int totalNoOfProfiles)
{
this.totalNoOfProfiles = totalNoOfProfiles;
}
public int getTotalNoOfProfiles()
{
return totalNoOfProfiles;
}
public void setDefaultProfileID(String ID)
public void setDefaultProfileID(String ID)
{
{
defaultProfileID = ID;
defaultProfileID = ID;
}
}
public void addTheme(ClientTheme clientTheme) throws CloneNotSupportedException
public void addTheme(ClientTheme clientTheme) throws CloneNotSupportedException
{
{
themes.put(clientTheme.getThemeFullName(), (ClientTheme) clientTheme.clone());
themes.put(clientTheme.getThemeFullName(), (ClientTheme) clientTheme.clone());
}
}
public ArrayList<ClientTheme> getThemes()
public ArrayList<ClientTheme> getThemes()
{
{
ArrayList<ClientTheme> clientThemes = new ArrayList<>();
ArrayList<ClientTheme> clientThemes = new ArrayList<>();
for(String clientTheme : themes.keySet())
for(String clientTheme : themes.keySet())
{
{
clientThemes.add(themes.get(clientTheme));
clientThemes.add(themes.get(clientTheme));
}
}
return clientThemes;
return clientThemes;
}
}
public ClientTheme getThemeByFullName(String fullName)
public ClientTheme getThemeByFullName(String fullName)
{
{
return themes.getOrDefault(fullName, null);
return themes.getOrDefault(fullName, null);
}
}
public String getDefaultProfileID()
public String getDefaultProfileID()
{
{
return defaultProfileID;
return defaultProfileID;
}
}
public void setConnectionHandler(ClientConnection connectionHandler)
{
this.connectionHandler = connectionHandler;
}
public ClientConnection getConnectionHandler()
{
return connectionHandler;
}
//Client Profiles
//Client Profiles
/*public ArrayList<ClientProfile> getProfiles()
{
return profiles;
}*/
public void setNickName(String nickName)
public void setNickName(String nickName)
{
{
this.nickName = nickName;
this.nickName = nickName;
}
}
public List<ClientProfile> getAllClientProfiles()
public List<ClientProfile> getAllClientProfiles()
{
{
ArrayList<ClientProfile> clientProfiles = new ArrayList<>();
ArrayList<ClientProfile> clientProfiles = new ArrayList<>();
for(String profile : profiles.keySet())
for(String profile : profiles.keySet())
clientProfiles.add(profiles.get(profile));
clientProfiles.add(profiles.get(profile));
return clientProfiles;
return clientProfiles;
}
}
public void removeProfileFromID(String ID) throws MinorException {
public void removeProfileFromID(String ID)
{
profiles.remove(ID);
profiles.remove(ID);
}
}
public void addProfile(ClientProfile clientProfile) throws CloneNotSupportedException {
public void addProfile(ClientProfile clientProfile) throws CloneNotSupportedException {
profiles.put(clientProfile.getID(), (ClientProfile) clientProfile.clone());
profiles.put(clientProfile.getID(), (ClientProfile) clientProfile.clone());
}
}
public synchronized ClientProfile getProfileByID(String ID) {
public synchronized ClientProfile getProfileByID(String ID) {
return profiles.getOrDefault(ID, null);
return profiles.getOrDefault(ID, null);
}
}
public SocketAddress getRemoteSocketAddress()
public SocketAddress getRemoteSocketAddress()
{
{
return remoteSocketAddress;
return remoteSocketAddress;
}
}
public Platform getPlatform()
public Platform getPlatform()
{
{
return platform;
return platform;
}
}
public String getNickName()
public String getNickName()
{
{
return nickName;
return nickName;
}
}
public Version getVersion()
public Version getVersion()
{
{
return version;
return version;
}
}
public Version getCommStandardVersion()
public Version getCommStandardVersion()
{
{
return commStandardVersion;
return commStandardVersion;
}
}
public Version getThemeAPIVersion()
public Version getThemeAPIVersion()
{
{
return themeAPIVersion;
return themeAPIVersion;
}
}
public double getStartupDisplayHeight()
public double getStartupDisplayHeight()
{
{
return startupDisplayHeight;
return startupDisplayHeight;
}
}
public double getStartupDisplayWidth()
public double getStartupDisplayWidth()
{
{
return startupDisplayWidth;
return startupDisplayWidth;
}
}
public void setStartupDisplayHeight(double height)
public void setStartupDisplayHeight(double height)
{
{
startupDisplayHeight = height;
startupDisplayHeight = height;
}
}
public void setStartupDisplayWidth(double width)
public void setStartupDisplayWidth(double width)
{
{
startupDisplayWidth = width;
startupDisplayWidth = width;
}
}
private int getMaxRows(int eachActionSize)
private int getMaxRows(int eachActionSize)
{
{
return (int) (startupDisplayHeight / eachActionSize);
return (int) (startupDisplayHeight / eachActionSize);
}
}
public int getMaxCols(int eachActionSize)
public int getMaxCols(int eachActionSize)
{
{
return (int) (startupDisplayWidth / eachActionSize);
return (int) (startupDisplayWidth / eachActionSize);
}
}
}
}
/*
Stream-Pi - Free & Open-Source Modular Cross-Platform Programmable Macropad
Copyright (C) 2019-2021 Debayan Sutradhar (rnayabed), Samuel Quiñones (SamuelQuinones)
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Written by : Debayan Sutradhar (rnayabed)
*/
package com.StreamPi.Server.Client;
package com.StreamPi.Server.Client;
import com.StreamPi.ActionAPI.Action.Action;
import com.StreamPi.ActionAPI.Action.Action;
import com.StreamPi.ActionAPI.Action.ActionType;
import com.StreamPi.ActionAPI.Action.DisplayTextAlignment;
import com.StreamPi.ActionAPI.Action.Location;
import com.StreamPi.ActionAPI.ActionProperty.ClientProperties;
import com.StreamPi.ActionAPI.NormalAction.NormalAction;
import com.StreamPi.Server.Action.NormalActionPlugins;
import com.StreamPi.Server.Window.Dashboard.ActionGridPane.ActionBox;
import com.StreamPi.Util.Exception.MinorException;
import javafx.geometry.Dimension2D;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashMap;
import java.util.Set;
import java.util.Set;
import java.util.UUID;
import java.util.UUID;
public class ClientProfile implements Cloneable {
public class ClientProfile implements Cloneable {
private String name, ID;
private String name, ID;
private int rows, cols, actionSize, actionGap;
private int rows, cols, actionSize, actionGap;
private final HashMap<String, Action> actions;
private final HashMap<String, Action> actions;
public ClientProfile(String name, String ID, int rows, int cols, int actionSize, int actionGap)
public ClientProfile(String name, String ID, int rows, int cols, int actionSize, int actionGap)
{
{
this.actions = new HashMap<>();
this.actions = new HashMap<>();
this.ID = ID;
this.ID = ID;
this.name = name;
this.name = name;
this.rows = rows;
this.rows = rows;
this.cols = cols;
this.cols = cols;
this.actionGap = actionGap;
this.actionGap = actionGap;
this.actionSize = actionSize;
this.actionSize = actionSize;
}
}
public ClientProfile(String name, int rows, int cols, int actionSize, int actionGap)
public ClientProfile(String name, int rows, int cols, int actionSize, int actionGap)
{
{
this(name, UUID.randomUUID().toString(), rows, cols, actionSize, actionGap);
this(name, UUID.randomUUID().toString(), rows, cols, actionSize, actionGap);
}
}
public Action getActionByID(String ID)
public Action getActionByID(String ID)
{
{
return actions.get(ID);
return actions.get(ID);
}
}
public void removeActionByID(String ID)
public void removeActionByID(String ID)
{
{
actions.remove(ID);
actions.remove(ID);
}
}
public Set<String> getActionsKeySet() {
public Set<String> getActionsKeySet() {
return actions.keySet();
return actions.keySet();
}
}
public synchronized void addAction(Action action) throws CloneNotSupportedException {
public synchronized void addAction(Action action) throws CloneNotSupportedException {
actions.put(action.getID(), action.clone());
actions.put(action.getID(), action.clone());
}
}
public String getID()
public String getID()
{
{
return ID;
return ID;
}
}
public String getName()
public String getName()
{
{
return name;
return name;
}
}
public int getRows()
public int getRows()
{
{
return rows;
return rows;
}
}
public int getCols()
public int getCols()
{
{
return cols;
return cols;
}
}
public int getActionSize()
public int getActionSize()
{
{
return actionSize;
return actionSize;
}
}
public int getActionGap()
public int getActionGap()
{
{
return actionGap;
return actionGap;
}
}
public void setRows(int rows)
public void setRows(int rows)
{
{
this.rows = rows;
this.rows = rows;
}
}
public void setCols(int cols)
public void setCols(int cols)
{
{
this.cols = cols;
this.cols = cols;
}
}
public void setID(String ID)
public void setID(String ID)
{
{
this.ID = ID;
this.ID = ID;
}
}
public void setActionSize(int actionSize)
public void setActionSize(int actionSize)
{
{
this.actionSize = actionSize;
this.actionSize = actionSize;
}
}
public void setActionGap(int actionGap)
public void setActionGap(int actionGap)
{
{
this.actionGap = actionGap;
this.actionGap = actionGap;
}
}
public void setName(String name)
public void setName(String name)
{
{
this.name = name;
this.name = name;
}
}
public Object clone() throws CloneNotSupportedException
public Object clone() throws CloneNotSupportedException
{
{
return super.clone();
return super.clone();
}
}
}
}
package com.StreamPi.Server.Connection;
package com.StreamPi.Server.Connection;
import com.StreamPi.ActionAPI.Action.Action;
import com.StreamPi.ActionAPI.Action.Action;
import com.StreamPi.ActionAPI.Action.ActionType;
import com.StreamPi.ActionAPI.Action.ActionType;
import com.StreamPi.ActionAPI.Action.DisplayTextAlignment;
import com.StreamPi.ActionAPI.Action.DisplayTextAlignment;
import com.StreamPi.ActionAPI.Action.Location;
import com.StreamPi.ActionAPI.Action.Location;
import com.StreamPi.ActionAPI.ActionProperty.ClientProperties;
import com.StreamPi.ActionAPI.ActionProperty.ClientProperties;
import com.StreamPi.ActionAPI.ActionProperty.Property.Property;
import com.StreamPi.ActionAPI.ActionProperty.Property.Property;
import com.StreamPi.ActionAPI.ActionProperty.Property.Type;
import com.StreamPi.ActionAPI.ActionProperty.Property.Type;
import com.StreamPi.ActionAPI.NormalAction.NormalAction;
import com.StreamPi.ActionAPI.NormalAction.NormalAction;
import com.StreamPi.ActionAPI.OtherActions.CombineAction;
import com.StreamPi.ActionAPI.OtherActions.CombineAction;
import com.StreamPi.ActionAPI.OtherActions.FolderAction;
import com.StreamPi.ActionAPI.OtherActions.FolderAction;
import com.StreamPi.Server.Action.NormalActionPlugins;
import com.StreamPi.Server.Action.NormalActionPlugins;
import com.StreamPi.Server.Client.Client;
import com.StreamPi.Server.Client.Client;
import com.StreamPi.Server.Client.ClientProfile;
import com.StreamPi.Server.Client.ClientProfile;
import com.StreamPi.Server.Client.ClientTheme;
import com.StreamPi.Server.Client.ClientTheme;
import com.StreamPi.Server.Info.ServerInfo;
import com.StreamPi.Server.Info.ServerInfo;
import com.StreamPi.Server.Window.ExceptionAndAlertHandler;
import com.StreamPi.Server.Window.ExceptionAndAlertHandler;
import com.StreamPi.Util.Alert.StreamPiAlert;
import com.StreamPi.Util.Alert.StreamPiAlert;
import com.StreamPi.Util.Alert.StreamPiAlertType;
import com.StreamPi.Util.Alert.StreamPiAlertType;
import com.StreamPi.Util.Exception.MinorException;
import com.StreamPi.Util.Exception.MinorException;
import com.StreamPi.Util.Exception.SevereException;
import com.StreamPi.Util.Exception.SevereException;
import com.StreamPi.Util.Exception.StreamPiException;
import com.StreamPi.Util.Exception.StreamPiException;
import com.StreamPi.Util.Platform.Platform;
import com.StreamPi.Util.Platform.Platform;
import com.StreamPi.Util.Platform.ReleaseStatus;
import com.StreamPi.Util.Platform.ReleaseStatus;
import com.StreamPi.Util.Version.Version;
import com.StreamPi.Util.Version.Version;
import javafx.concurrent.Task;
import javafx.concurrent.Task;
import java.io.ByteArrayOutputStream;
import java.io.ByteArrayOutputStream;
import java.io.DataInputStream;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.ServerSocket;
import java.net.Socket;
import java.net.Socket;
import java.net.SocketException;
import java.net.SocketException;
import java.net.SocketTimeoutException;
import java.net.SocketTimeoutException;
import java.nio.ByteBuffer;
import java.nio.ByteBuffer;
import java.nio.charset.Charset;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.ArrayList;
import java.util.List;
import java.util.List;
import java.util.Random;
import java.util.Random;
import java.util.UUID;
import java.util.UUID;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.logging.Level;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.logging.Logger;
import java.util.stream.Stream;
import java.util.stream.Stream;
public class ClientConnection extends Thread{
public class ClientConnection extends Thread{
private Socket socket;
private Socket socket;
private ServerListener serverListener;
private ServerListener serverListener;
private AtomicBoolean stop = new AtomicBoolean(false);
private AtomicBoolean stop = new AtomicBoolean(false);
private DataInputStream dis;
private DataInputStream dis;
private DataOutputStream dos;
private DataOutputStream dos;
private Logger logger;
private Logger logger;
private Client client = null;
private Client client = null;
private ExceptionAndAlertHandler exceptionAndAlertHandler;
private ExceptionAndAlertHandler exceptionAndAlertHandler;
public ClientConnection(Socket socket, ServerListener serverListener, ExceptionAndAlertHandler exceptionAndAlertHandler)
public ClientConnection(Socket socket, ServerListener serverListener, ExceptionAndAlertHandler exceptionAndAlertHandler)
{
{
this.exceptionAndAlertHandler = exceptionAndAlertHandler;
this.exceptionAndAlertHandler = exceptionAndAlertHandler;
//actionIconsToBeSent = new ArrayList__();
//actionIconsToBeSent = new ArrayList__();
this.socket = socket;
this.socket = socket;
this.serverListener = serverListener;
this.serverListener = serverListener;
logger = Logger.getLogger(ClientConnection.class.getName());
logger = Logger.getLogger(ClientConnection.class.getName());
try
try
{
{
dis = new DataInputStream(socket.getInputStream());
dis = new DataInputStream(socket.getInputStream());
dos = new DataOutputStream(socket.getOutputStream());
dos = new DataOutputStream(socket.getOutputStream());
} catch (IOException e) {
} catch (IOException e) {
e.printStackTrace();
e.printStackTrace();
exceptionAndAlertHandler.handleMinorException(new MinorException("Unable to start socket streams"));
exceptionAndAlertHandler.handleMinorException(new MinorException("Unable to start socket streams"));
}
}
start();
start();
}
}
public synchronized void exit()
public synchronized void exit()
{
{
if(stop.get())
if(stop.get())
return;
return;
logger.info("Stopping ...");
logger.info("Stopping ...");
try
try
{
{
if(socket !=null)
if(socket !=null)
{
{
logger.info("Stopping connection "+socket.getRemoteSocketAddress());
logger.info("Stopping connection "+socket.getRemoteSocketAddress());
disconnect();
disconnect();
}
}
}
}
catch (SevereException e)
catch (SevereException e)
{
{
e.printStackTrace();
e.printStackTrace();
exceptionAndAlertHandler.handleSevereException(e);
exceptionAndAlertHandler.handleSevereException(e);
}
}
}
}
public synchronized void exitAndRemove()
public synchronized void exitAndRemove()
{
{
exit();
exit();
removeConnection();
removeConnection();
serverListener.clearTemp();
serverListener.clearTemp();
}
}
public void removeConnection()
public void removeConnection()
{
{
ClientConnections.getInstance().removeConnection(this);
ClientConnections.getInstance().removeConnection(this);
}
}
public void writeToStream(String text) throws SevereException
public void writeToStream(String text) throws SevereException
{
{
/*try
/*try
{
{
logger.debug(text);
logger.debug(text);
dos.writeUTF(text);
dos.writeUTF(text);
dos.flush();
dos.flush();
}
}
catch (IOException e)
catch (IOException e)
{
{
e.printStackTrace();
e.printStackTrace();
throw new SevereException("Unable to write to IO Stream!");
throw new SevereException("Unable to write to IO Stream!");
}*/
}*/
try
try
{
{
byte[] txtBytes = text.getBytes();
byte[] txtBytes = text.getBytes();
Thread.sleep(50);
Thread.sleep(50);
dos.writeUTF("string:: ::");
dos.writeUTF("string:: ::");
dos.flush();
dos.flush();
dos.writeInt(txtBytes.length);
dos.writeInt(txtBytes.length);
dos.flush();
dos.flush();
write(txtBytes);
write(txtBytes);
dos.flush();
dos.flush();
}
}
catch (IOException | InterruptedException e)
catch (IOException | InterruptedException e)
{
{
e.printStackTrace();
e.printStackTrace();
throw new SevereException("Unable to write to IO Stream!");
throw new SevereException("Unable to write to IO Stream!");
}
}
}
}
public void sendIcon(String profileID, String actionID, byte[] icon) throws SevereException
public void sendIcon(String profileID, String actionID, byte[] icon) throws SevereException
{
{
try
try
{
{
logger.info("Sending action Icon...");
logger.info("Sending action Icon...");
//Thread.sleep(50);
//Thread.sleep(50);
System.out.println("1");
System.out.println("1");
dos.writeUTF("action_icon::"+profileID+"!!"+actionID+"!!::"+icon.length);
dos.writeUTF("action_icon::"+profileID+"!!"+actionID+"!!::"+icon.length);
System.out.println("2");
System.out.println("2");
dos.flush();
dos.flush();
System.out.println("3");
System.out.println("3");
dos.writeInt(icon.length);
dos.writeInt(icon.length);
System.out.println("4");
System.out.println("4");
dos.flush();
dos.flush();
System.out.println("5");
System.out.println("5");
write(icon);
write(icon);
System.out.println("6");
System.out.println("6");
dos.flush();
dos.flush();
System.out.println("7");
System.out.println("7");
}
}
catch (IOException e)
catch (IOException e)
{
{
e.printStackTrace();
e.printStackTrace();
throw new SevereException("Unable to write to IO Stream!");
throw new SevereException("Unable to write to IO Stream!");
}
}
}
}
public void write(byte[] array) throws SevereException
public void write(byte[] array) throws SevereException
{
{
try
try
{
{
dos.write(array);
dos.write(array);
}
}
catch (IOException e)
catch (IOException e)
{
{
e.printStackTrace();
e.printStackTrace();
throw new SevereException("Unable to write to IO Stream!");
throw new SevereException("Unable to write to IO Stream!");
}
}
}
}
public void initAfterConnectionQueryReceive(String[] arr) throws StreamPiException
public void initAfterConnectionQueryReceive(String[] arr) throws StreamPiException
{
{
logger.info("Setting up Client object ...");
logger.info("Setting up Client object ...");
Version clientVersion;
Version clientVersion;
Version commsStandard;
Version commsStandard;
Version themesStandard;
Version themesStandard;
ReleaseStatus releaseStatus;
ReleaseStatus releaseStatus;
try
try
{
{
clientVersion = new Version(arr[1]);
clientVersion = new Version(arr[1]);
releaseStatus = ReleaseStatus.valueOf(arr[2]);
releaseStatus = ReleaseStatus.valueOf(arr[2]);
commsStandard = new Version(arr[3]);
commsStandard = new Version(arr[3]);
themesStandard = new Version(arr[4]);
themesStandard = new Version(arr[4]);
}
}
catch (MinorException e)
catch (MinorException e)
{
{
exitAndRemove();
exitAndRemove();
throw new MinorException(e.getShortMessage()+" (Client '"+socket.getRemoteSocketAddress()+"' )");
throw new MinorException(e.getShortMessage()+" (Client '"+socket.getRemoteSocketAddress()+"' )");
}
}
if(!commsStandard.isEqual(ServerInfo.getInstance().getCommStandardVersion()))
if(!commsStandard.isEqual(ServerInfo.getInstance().getCommStandardVersion()))
{
{
String errTxt = "Server and Client Communication standards do not match. Make sure you are on the latest version of server and client.\n" +
String errTxt = "Server and Client Communication standards do not match. Make sure you are on the latest version of server and client.\n" +
"Server Comms. Standard : "+ServerInfo.getInstance().getCommStandardVersion().getText()+
"Server Comms. Standard : "+ServerInfo.getInstance().getCommStandardVersion().getText()+
"\nClient Comms. Standard : "+commsStandard.getText();
"\nClient Comms. Standard : "+commsStandard.getText();
disconnect(errTxt);
disconnect(errTxt);
throw new MinorException(errTxt);
throw new MinorException(errTxt);
}
}
client = new Client(clientVersion, releaseStatus, commsStandard, themesStandard, arr[5], Platform.valueOf(arr[8]), socket.getRemoteSocketAddress());
client = new Client(clientVersion, releaseStatus, commsStandard, themesStandard, arr[5], Platform.valueOf(arr[8]), socket.getRemoteSocketAddress());
client.setStartupDisplayWidth(Double.parseDouble(arr[6]));
client.setStartupDisplayWidth(Double.parseDouble(arr[6]));
client.setStartupDisplayHeight(Double.parseDouble(arr[7]));
client.setStartupDisplayHeight(Double.parseDouble(arr[7]));
client.setDefaultProfileID(arr[9]);
client.setDefaultProfileID(arr[9]);
client.setDefaultThemeFullName(arr[10]);
client.setDefaultThemeFullName(arr[10]);
//call get profiles command.
//call get profiles command.
serverListener.clearTemp();
serverListener.clearTemp();
}
}
public synchronized Client getClient()
public synchronized Client getClient()
{
{
return client;
return client;
}
}
@Override
@Override
public void run() {
public void run() {
try {
try {
initAfterConnectionQuerySend();
initAfterConnectionQuerySend();
} catch (SevereException e) {
} catch (SevereException e) {
e.printStackTrace();
e.printStackTrace();
exceptionAndAlertHandler.handleSevereException(e);
exceptionAndAlertHandler.handleSevereException(e);
exitAndRemove();
exitAndRemove();
return;
return;
}
}
try
try
{
{
while(!stop.get())
while(!stop.get())
{
{
String msg = "";
String msg = "";
try
try
{
{
String raw = dis.readUTF();
String raw = dis.readUTF();
int length = dis.readInt();
int length = dis.readInt();
System.out.println("SIZE TO READ : "+length);
System.out.println("SIZE TO READ : "+length);
String[] precursor = raw.split("::");
String[] precursor = raw.split("::");
String inputType = precursor[0];
String inputType = precursor[0];
String secondArg = precursor[1];
String secondArg = precursor[1];
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
/*int count;
/*int count;
int chunkSize = 512;
int chunkSize = 512;
while (length>0)
while (length>0)
{
{
if(chunkSize > length)
if(chunkSize > length)
chunkSize = length;
chunkSize = length;
else
else
chunkSize = 512;
chunkSize = 512;
byte[] buffer = new byte[chunkSize];
byte[] buffer = new byte[chunkSize];
count = dis.read(buffer);
count = dis.read(buffer);
System.out.println(count);
System.out.println(count);
byteArrayOutputStream.write(buffer);
byteArrayOutputStream.write(buffer);
length-=count;
length-=count;
}*/
}*/
/*byte[] buffer = new byte[8192];
/*byte[] buffer = new byte[8192];
int read;
int read;
while((read = dis.read(buffer)) != -1){
while((read = dis.read(buffer)) != -1){
System.out.println("READ : "+read);
System.out.println("READ : "+read);
byteArrayOutputStream.write(buffer, 0, read);
byteArrayOutputStream.write(buffer, 0, read);
}
}
System.out.println("READ : "+byteArrayOutputStream.size());
System.out.println("READ : "+byteArrayOutputStream.size());
byteArrayOutputStream.close();
byteArrayOutputStream.close();
byte[] bArr = byteArrayOutputStream.toByteArray();*/
byte[] bArr = byteArrayOutputStream.toByteArray();*/
byte[] bArr = new byte[length];
byte[] bArr = new byte[length];
dis.readFully(bArr);
dis.readFully(bArr);
if(inputType.equals("string"))
if(inputType.equals("string"))
{
{
msg = new String(bArr);
msg = new String(bArr);
}
}
else if(inputType.equals("action_icon"))
else if(inputType.equals("action_icon"))
{
{
String[] secondArgSep = secondArg.split("!!");
String[] secondArgSep = secondArg.split("!!");
String profileID = secondArgSep[0];
String profileID = secondArgSep[0];
String actionID = secondArgSep[1];
String actionID = secondArgSep[1];
getClient().getProfileByID(profileID).getActionByID(actionID).setIcon(bArr);
getClient().getProfileByID(profileID).getActionByID(actionID).setIcon(bArr);
//serverListener.clearTemp();
//serverListener.clearTemp();
continue;
continue;
}
}
}
}
catch (IOException e)
catch (IOException e)
{
{
logger.log(Level.SEVERE, e.getMessage());
logger.log(Level.SEVERE, e.getMessage());
e.printStackTrace();
e.printStackTrace();
serverListener.clearTemp();
serverListener.clearTemp();
if(!stop.get())
if(!stop.get())
{
{
removeConnection();
removeConnection();
throw new MinorException("Accidentally disconnected from "+getClient().getNickName()+".");
throw new MinorException("Accidentally disconnected from "+getClient().getNickName()+".");
}
}
exitAndRemove();
exitAndRemove();
return;
return;
}
}
logger.info("Received text : '"+msg+"'");
logger.info("Received text : '"+msg+"'");
String[] sep = msg.split("::");
String[] sep = msg.split("::");
String command = sep[0];
String command = sep[0];
switch (command)
switch (command)
{
{
case "disconnect" : clientDisconnected(msg);
case "disconnect" : clientDisconnected(msg);
break;
break;
case "client_details" : initAfterConnectionQueryReceive(sep);
case "client_details" : initAfterConnectionQueryReceive(sep);
getProfilesFromClient();
getProfilesFromClient();
getThemesFromClient();
getThemesFromClient();
break;
break;
case "profiles" : registerProfilesFromClient(sep);
case "profiles" : registerProfilesFromClient(sep);
break;
break;
case "profile_details" : registerProfileDetailsFromClient(sep);
case "profile_details" : registerProfileDetailsFromClient(sep);
break;
break;
case "action_details" : registerActionToProfile(sep);
case "action_details" : registerActionToProfile(sep);
break;
break;
case "themes": registerThemes(sep);
case "themes": registerThemes(sep);
break;
break;
case "action_clicked": actionClicked(sep[1], sep[2]);
case "action_clicked": actionClicked(sep[1], sep[2]);
break;
break;
default: logger.warning("Command '"+command+"' does not match records. Make sure client and server versions are equal.");
default: logger.warning("Command '"+command+"' does not match records. Make sure client and server versions are equal.");
}
}
}
}
}
}
catch (StreamPiException e)
catch (StreamPiException e)
{
{
e.printStackTrace();
e.printStackTrace();
if(e instanceof MinorException)
if(e instanceof MinorException)
exceptionAndAlertHandler.handleMinorException((MinorException) e);
exceptionAndAlertHandler.handleMinorException((MinorException) e);
else if (e instanceof SevereException)
else if (e instanceof SevereException)
exceptionAndAlertHandler.handleSevereException((SevereException) e);
exceptionAndAlertHandler.handleSevereException((SevereException) e);
}
}
}
}
// commands
// commands
public void initAfterConnectionQuerySend() throws SevereException
public void initAfterConnectionQuerySend() throws SevereException
{
{
logger.info("Asking client details ...");
logger.info("Asking client details ...");
writeToStream("get_client_details::");
writeToStream("get_client_details::");
}
}
public void disconnect() throws SevereException {
public void disconnect() throws SevereException {
disconnect("");
disconnect("");
}
}
public void disconnect(String message) throws SevereException {
public void disconnect(String message) throws SevereException {
if(stop.get())
if(stop.get())
return;
return;
stop.set(true);
stop.set(true);
logger.info("Sending client disconnect message ...");
logger.info("Sending client disconnect message ...");
writeToStream("disconnect::"+message+"::");
writeToStream("disconnect::"+message+"::");
try
try
{
{
if(!socket.isClosed())
if(!socket.isClosed())
socket.close();
socket.close();
}
}
catch (IOException e)
catch (IOException e)
{
{
e.printStackTrace();
e.printStackTrace();
throw new SevereException("Unable to close socket");
throw new SevereException("Unable to close socket");
}
}
}
}
public void clientDisconnected(String message)
public void clientDisconnected(String message)
{
{
stop.set(true);
stop.set(true);
String txt = "Disconnected!";
String txt = "Disconnected!";
if(!message.equals("disconnect::::"))
if(!message.equals("disconnect::::"))
txt = "Message : "+message.split("::")[1];
txt = "Message : "+message.split("::")[1];
new StreamPiAlert("Disconnected from "+getClient().getNickName()+".", txt, StreamPiAlertType.WARNING).show();;
new StreamPiAlert("Disconnected from "+getClient().getNickName()+".", txt, StreamPiAlertType.WARNING).show();;
exitAndRemove();
exitAndRemove();
}
}
public void getProfilesFromClient() throws StreamPiException
public void getProfilesFromClient() throws StreamPiException
{
{
logger.info("Asking client to send profiles ...");
logger.info("Asking client to send profiles ...");
writeToStream("get_profiles::");
writeToStream("get_profiles::");
}
}
public void getThemesFromClient() throws StreamPiException
public void getThemesFromClient() throws StreamPiException
{
{
logger.info("Asking clients to send themes ...");
logger.info("Asking clients to send themes ...");
writeToStream("get_themes::");
writeToStream("get_themes::");
}
}
public void registerThemes(String[] sep)
public void registerThemes(String[] sep)
{
{
for(int i =1; i<sep.length;i++)
for(int i =1; i<sep.length;i++)
{
{
String[] internal = sep[i].split("__");
String[] internal = sep[i].split("__");
ClientTheme clientTheme = new ClientTheme(
ClientTheme clientTheme = new ClientTheme(
internal[0],
internal[0],
internal[1],
internal[1],
internal[2],
internal[2],
internal[3]
internal[3]
);
);
try
try
{
{
getClient().addTheme(clientTheme);
getClient().addTheme(clientTheme);
}
}
catch (CloneNotSupportedException e)
catch (CloneNotSupportedException e)
{
{
logger.log(Level.SEVERE, e.getMessage());
logger.log(Level.SEVERE, e.getMessage());
e.printStackTrace();
e.printStackTrace();
}
}
}
}
}
}
public void registerProfilesFromClient(String[] sep) throws StreamPiException
public void registerProfilesFromClient(String[] sep) throws StreamPiException
{
{
logger.info("Registering profiles ...");
logger.info("Registering profiles ...");
int noOfProfiles = Integer.parseInt(sep[1]);
int noOfProfiles = Integer.parseInt(sep[1]);
getClient().setTotalNoOfProfiles(noOfProfiles);
for(int i = 2; i<(noOfProfiles + 2); i++)
for(int i = 2; i<(noOfProfiles + 2); i++)
{
{
String profileID = sep[i];
String profileID = sep[i];
getProfileDetailsFromClient(profileID);
getProfileDetailsFromClient(profileID);
}
}
}
}
public void getProfileDetailsFromClient(String ID) throws StreamPiException
public void getProfileDetailsFromClient(String ID) throws StreamPiException
{
{
logger.info("Asking client to send details of profile : "+ID);
logger.info("Asking client to send details of profile : "+ID);
writeToStream("get_profile_details::"+ID+"::");
writeToStream("get_profile_details::"+ID+"::");
}
}
public void registerProfileDetailsFromClient(String[] sep)
public void registerProfileDetailsFromClient(String[] sep)
{
{
String ID = sep[1];
String ID = sep[1];
logger.info("Registering details for profile : "+ID);
logger.info("Registering details for profile : "+ID);
String name = sep[2];
String name = sep[2];
int rows = Integer.parseInt(sep[3]);
int rows = Integer.parseInt(sep[3]);
int cols = Integer.parseInt(sep[4]);
int cols = Integer.parseInt(sep[4]);
int actionSize = Integer.parseInt(sep[5]);
int actionSize = Integer.parseInt(sep[5]);
int actionGap = Integer.parseInt(sep[6]);
int actionGap = Integer.parseInt(sep[6]);
ClientProfile clientProfile = new ClientProfile(name, ID, rows, cols, actionSize, actionGap);
ClientProfile clientProfile = new ClientProfile(name, ID, rows, cols, actionSize, actionGap);
logger.info("Added client profile "+clientProfile.getName());
logger.info("Added client profile "+clientProfile.getName());
try
try
{
{
getClient().addProfile(clientProfile);
getClient().addProfile(clientProfile);
}
}
catch (CloneNotSupportedException e)
catch (CloneNotSupportedException e)
{
{
logger.severe(e.getMessage());
logger.severe(e.getMessage());
e.printStackTrace();
e.printStackTrace();
}
}
serverListener.clearTemp();
serverListener.clearTemp();
}
}
/*public void getActionIcon(String profileID, String actionID) throws StreamPiException
/*public void getActionIcon(String profileID, String actionID) throws StreamPiException
{
{
System.out.println("getting action icon from "+profileID+", "+actionID);
System.out.println("getting action icon from "+profileID+", "+actionID);
writeToStream("get_action_icon::"+profileID+"::"+actionID);
writeToStream("get_action_icon::"+profileID+"::"+actionID);
}*/
}*/
public synchronized void registerActionToProfile(String[] sep) throws StreamPiException
public synchronized void registerActionToProfile(String[] sep) throws StreamPiException
{
{
String profileID = sep[1];
String profileID = sep[1];
String ID = sep[2];
String ID = sep[2];
ActionType actionType = ActionType.valueOf(sep[3]);
ActionType actionType = ActionType.valueOf(sep[3]);
//4 - Version
//4 - Version
//5 - ModuleName
//5 - ModuleName
//display
//display
String bgColorHex = sep[6];
String bgColorHex = sep[6];
//icon
//icon
boolean isHasIcon = sep[7].equals("true");
boolean isHasIcon = sep[7].equals("true");
boolean isShowIcon = sep[8].equals("true");
boolean isShowIcon = sep[8].equals("true");
//text
//text
boolean isShowDisplayText = sep[9].equals("true");
boolean isShowDisplayText = sep[9].equals("true");
String displayFontColor = sep[10];
String displayFontColor = sep[10];
String displayText = sep[11];
String displayText = sep[11];
DisplayTextAlignment displayTextAlignment = DisplayTextAlignment.valueOf(sep[12]);
DisplayTextAlignment displayTextAlignment = DisplayTextAlignment.valueOf(sep[12]);
//location
//location
String row = sep[13];
String row = sep[13];
String col = sep[14];
String col = sep[14];
Location location = new Location(Integer.parseInt(row), Integer.parseInt(col));
Location location = new Location(Integer.parseInt(row), Integer.parseInt(col));
Action action = new Action(ID, actionType);
Action action = new Action(ID, actionType);
action.setBgColourHex(bgColorHex);
action.setBgColourHex(bgColorHex);
action.setShowIcon(isShowIcon);
action.setShowIcon(isShowIcon);
action.setHasIcon(isHasIcon);
action.setHasIcon(isHasIcon);
action.setShowDisplayText(isShowDisplayText);
action.setShowDisplayText(isShowDisplayText);
action.setDisplayTextFontColourHex(displayFontColor);
action.setDisplayTextFontColourHex(displayFontColor);
action.setDisplayText(displayText);
action.setDisplayText(displayText);
action.setDisplayTextAlignment(displayTextAlignment);
action.setDisplayTextAlignment(displayTextAlignment);
action.setLocation(location);
action.setLocation(location);
//client properties
//client properties
int clientPropertiesSize = Integer.parseInt(sep[15]);
int clientPropertiesSize = Integer.parseInt(sep[15]);
String root = sep[17];
String root = sep[17];
action.setParent(root);
action.setParent(root);
String[] clientPropertiesRaw = sep[16].split("!!");
String[] clientPropertiesRaw = sep[16].split("!!");
ClientProperties clientProperties = new ClientProperties();
ClientProperties clientProperties = new ClientProperties();
if(actionType == ActionType.FOLDER)
if(actionType == ActionType.FOLDER)
clientProperties.setDuplicatePropertyAllowed(true);
clientProperties.setDuplicatePropertyAllowed(true);
for(int i = 0;i<clientPropertiesSize; i++)
for(int i = 0;i<clientPropertiesSize; i++)
{
{
String[] clientPraw = clientPropertiesRaw[i].split("__");
String[] clientPraw = clientPropertiesRaw[i].split("__");
Property property = new Property(clientPraw[0], Type.STRING);
Property property = new Property(clientPraw[0], Type.STRING);
if(clientPraw.length > 1)
if(clientPraw.length > 1)
property.setRawValue(clientPraw[1]);
property.setRawValue(clientPraw[1]);
clientProperties.addProperty(property);
clientProperties.addProperty(property);
}
}
action.setClientProperties(clientProperties);
action.setClientProperties(clientProperties);
action.setModuleName(sep[5]);
action.setModuleName(sep[5]);
//set up action
//set up action
//Action toBeAdded = null;
//Action toBeAdded = null;
if(actionType == ActionType.NORMAL)
if(actionType == ActionType.NORMAL)
{
{
NormalAction actionCopy = NormalActionPlugins.getInstance().getPluginByModuleName(sep[5]);
NormalAction actionCopy = NormalActionPlugins.getInstance().getPluginByModuleName(sep[5]);
if(actionCopy == null)
if(actionCopy == null)
{
{
action.setInvalid(true);
action.setInvalid(true);
}
}
else
else
{
{
action.setVersion(new Version(sep[4]));
action.setVersion(new Version(sep[4]));
//action.setHelpLink(actionCopy.getHelpLink());
//action.setHelpLink(actionCopy.getHelpLink());
if(actionCopy.getVersion().getMajor() != action.getVersion().getMajor())
if(actionCopy.getVersion().getMajor() != action.getVersion().getMajor())
{
{
action.setInvalid(true);
action.setInvalid(true);
}
}
else
else
{
{
action.setName(actionCopy.getName());
action.setName(actionCopy.getName());
ClientProperties finalClientProperties = new ClientProperties();
ClientProperties finalClientProperties = new ClientProperties();
for(Property property : actionCopy.getClientProperties().get())
for(Property property : actionCopy.getClientProperties().get())
{
{
for(int i = 0;i<action.getClientProperties().getSize();i++)
for(int i = 0;i<action.getClientProperties().getSize();i++)
{
{
Property property1 = action.getClientProperties().get().get(i);
Property property1 = action.getClientProperties().get().get(i);
if (property.getName().equals(property1.getName()))
if (property.getName().equals(property1.getName()))
{
{
property.setRawValue(property1.getRawValue());
property.setRawValue(property1.getRawValue());
finalClientProperties.addProperty(property);
finalClientProperties.addProperty(property);
}
}
}
}
}
}
action.setClientProperties(finalClientProperties);
action.setClientProperties(finalClientProperties);
}
}
}
}
}
}
try
try
{
{
for(Property prop : action.getClientProperties().get())
for(Property prop : action.getClientProperties().get())
{
{
logger.info("G@@@@@ : "+prop.getRawValue());
logger.info("G@@@@@ : "+prop.getRawValue());
}
}
getClient().getProfileByID(profileID).addAction(action);
getClient().getProfileByID(profileID).addAction(action);
for(String action1x : getClient().getProfileByID(profileID).getActionsKeySet())
for(String action1x : getClient().getProfileByID(profileID).getActionsKeySet())
{
{
Action action1 = getClient().getProfileByID(profileID).getActionByID(action1x);
Action action1 = getClient().getProfileByID(profileID).getActionByID(action1x);
logger.info("231cc : "+action1.getID());
logger.info("231cc : "+action1.getID());
for(Property prop : action1.getClientProperties().get())
for(Property prop : action1.getClientProperties().get())
{
{
logger.info("G@VVVV@@@ : "+prop.getRawValue());
logger.info("G@VVVV@@@ : "+prop.getRawValue());
}
}
}
}
}
}
catch (CloneNotSupportedException e)
catch (CloneNotSupportedException e)
{
{
e.printStackTrace();
e.printStackTrace();
exceptionAndAlertHandler.handleMinorException(new MinorException("Action", "Unable to clone"));
exceptionAndAlertHandler.handleMinorException(new MinorException("Action", "Unable to clone"));
}
}
}
}
public void saveActionDetails(String profileID, Action action) throws SevereException
public void saveActionDetails(String profileID, Action action) throws SevereException
{
{
StringBuilder finalQuery = new StringBuilder("save_action_details::");
StringBuilder finalQuery = new StringBuilder("save_action_details::");
//failsafes
//failsafes
if(action.getDisplayText().endsWith(":"))
if(action.getDisplayText().endsWith(":"))
action.setDisplayText(action.getDisplayText()+" ");
action.setDisplayText(action.getDisplayText()+" ");
finalQuery.append(profileID)
finalQuery.append(profileID)
.append("::")
.append("::")
.append(action.getID())
.append(action.getID())
.append("::")
.append("::")
.append(action.getActionType())
.append(action.getActionType())
.append("::");
.append("::");
if(action.getActionType() == ActionType.NORMAL)
if(action.getActionType() == ActionType.NORMAL)
{
{
finalQuery.append(action.getVersion().getText());
finalQuery.append(action.getVersion().getText());
System.out.println("VERSION :sdd "+action.getVersion().getText());
System.out.println("VERSION :sdd "+action.getVersion().getText());
}
}
finalQuery.append("::");
finalQuery.append("::");
if(action.getActionType() == ActionType.NORMAL)
if(action.getActionType() == ActionType.NORMAL)
finalQuery.append(action.getModuleName());
finalQuery.append(action.getModuleName());
finalQuery.append("::");
finalQuery.append("::");
//display
//display
finalQuery.append(action.getBgColourHex())
finalQuery.append(action.getBgColourHex())
.append("::");
.append("::");
//icon
//icon
finalQuery.append(action.isHasIcon())
finalQuery.append(action.isHasIcon())
.append("::")
.append("::")
.append(action.isShowIcon())
.append(action.isShowIcon())
.append("::");
.append("::");
//text
//text
finalQuery.append(action.isShowDisplayText())
finalQuery.append(action.isShowDisplayText())
.append("::")
.append("::")
.append(action.getDisplayTextFontColourHex())
.append(action.getDisplayTextFontColourHex())
.append("::")
.append("::")
.append(action.getDisplayText())
.append(action.getDisplayText())
.append("::")
.append("::")
.append(action.getDisplayTextAlignment())
.append(action.getDisplayTextAlignment())
.append("::");
.append("::");
//location
//location
if(action.getLocation() == null)
if(action.getLocation() == null)
finalQuery.append("-1::-1::");
finalQuery.append("-1::-1::");
else
else
finalQuery.append(action.getLocation().getRow())
finalQuery.append(action.getLocation().getRow())
.append("::")
.append("::")
.append(action.getLocation().getCol())
.append(action.getLocation().getCol())
.append("::");
.append("::");
//client properties
//client properties
ClientProperties clientProperties = action.getClientProperties();
ClientProperties clientProperties = action.getClientProperties();
finalQuery.append(clientProperties.getSize())
finalQuery.append(clientProperties.getSize())
.append("::");
.append("::");
for(Property property : clientProperties.get())
for(Property property : clientProperties.get())
{
{
finalQuery.append(property.getName())
finalQuery.append(property.getName())
.append("__")
.append("__")
.append(property.getRawValue())
.append(property.getRawValue())
.append("__");
.append("__");
finalQuery.append("!!");
finalQuery.append("!!");
}
}
finalQuery.append("::")
finalQuery.append("::")
.append(action.getParent())
.append(action.getParent())
.append("::");
.append("::");
writeToStream(finalQuery.toString());
writeToStream(finalQuery.toString());
}
}
public void deleteAction(String profileID, String actionID) throws SevereException
public void deleteAction(String profileID, String actionID) throws SevereException
{
{
writeToStream("delete_action::"+profileID+"::"+actionID);
writeToStream("delete_action::"+profileID+"::"+actionID);
}
}
public void saveClientDetails(String clientNickname, String screenWidth, String screenHeight, String defaultProfileID,
public void saveClientDetails(String clientNickname, String screenWidth, String screenHeight, String defaultProfileID,
String defaultThemeFullName) throws SevereException
String defaultThemeFullName) throws SevereException
{
{
writeToStream("save_client_details::"+
writeToStream("save_client_details::"+
clientNickname+"::"+
clientNickname+"::"+
screenWidth+"::"+
screenWidth+"::"+
screenHeight+"::"+
screenHeight+"::"+
defaultProfileID+"::"+
defaultProfileID+"::"+
defaultThemeFullName+"::");
defaultThemeFullName+"::");
client.setNickName(clientNickname);
client.setNickName(clientNickname);
client.setStartupDisplayWidth(Double.parseDouble(screenWidth));
client.setStartupDisplayWidth(Double.parseDouble(screenWidth));
client.setStartupDisplayHeight(Double.parseDouble(screenHeight));
client.setStartupDisplayHeight(Double.parseDouble(screenHeight));
client.setDefaultProfileID(defaultProfileID);
client.setDefaultProfileID(defaultProfileID);
client.setDefaultThemeFullName(defaultThemeFullName);
client.setDefaultThemeFullName(defaultThemeFullName);
}
}
public void saveProfileDetails(ClientProfile clientProfile) throws SevereException, CloneNotSupportedException {
public void saveProfileDetails(ClientProfile clientProfile) throws SevereException, CloneNotSupportedException {
if(client.getProfileByID(clientProfile.getID()) !=null)
if(client.getProfileByID(clientProfile.getID()) !=null)
{
{
client.getProfileByID(clientProfile.getID()).setName(clientProfile.getName());
client.getProfileByID(clientProfile.getID()).setName(clientProfile.getName());
client.getProfileByID(clientProfile.getID()).setRows(clientProfile.getRows());
client.getProfileByID(clientProfile.getID()).setRows(clientProfile.getRows());
client.getProfileByID(clientProfile.getID()).setCols(clientProfile.getCols());
client.getProfileByID(clientProfile.getID()).setCols(clientProfile.getCols());
client.getProfileByID(clientProfile.getID()).setActionSize(clientProfile.getActionSize());
client.getProfileByID(clientProfile.getID()).setActionSize(clientProfile.getActionSize());
client.getProfileByID(clientProfile.getID()).setActionGap(clientProfile.getActionGap());
client.getProfileByID(clientProfile.getID()).setActionGap(clientProfile.getActionGap());
}
}
else
else
client.addProfile(clientProfile);
client.addProfile(clientProfile);
writeToStream("save_client_profile::"+
writeToStream("save_client_profile::"+
clientProfile.getID()+"::"+
clientProfile.getID()+"::"+
clientProfile.getName()+"::"+
clientProfile.getName()+"::"+
clientProfile.getRows()+"::"+
clientProfile.getRows()+"::"+
clientProfile.getCols()+"::"+
clientProfile.getCols()+"::"+
clientProfile.getActionSize()+"::"+
clientProfile.getActionSize()+"::"+
clientProfile.getActionGap()+"::");
clientProfile.getActionGap()+"::");
}
}
public void deleteProfile(String ID) throws SevereException
public void deleteProfile(String ID) throws SevereException
{
{
writeToStream("delete_profile::"+ID+"::");
writeToStream("delete_profile::"+ID+"::");
}
}
public void actionClicked(String profileID, String actionID) {
public void actionClicked(String profileID, String actionID) {
try
try
{
{
Action action = client.getProfileByID(profileID).getActionByID(actionID);
Action action = client.getProfileByID(profileID).getActionByID(actionID);
if(action.getActionType() == ActionType.NORMAL)
if(action.getActionType() == ActionType.NORMAL)
{
{
NormalAction original = NormalActionPlugins.getInstance().getPluginByModuleName(
NormalAction original = NormalActionPlugins.getInstance().getPluginByModuleName(
action.getModuleName()
action.getModuleName()
);
);
if(original == null)
if(original == null)
{
{
throw new MinorException(
throw new MinorException(
"The Action isn't installed on the server."
"The Action isn't installed on the server."
);
);
}
}
NormalAction normalAction = original.clone();
NormalAction normalAction = original.clone();
normalAction.setLocation(action.getLocation());
normalAction.setLocation(action.getLocation());
normalAction.setDisplayText(action.getDisplayText());
normalAction.setDisplayText(action.getDisplayText());
normalAction.setID(actionID);
normalAction.setID(actionID);
normalAction.setClientProperties(action.getClientProperties());
normalAction.setClientProperties(action.getClientProperties());
new Thread(new Task<Void>() {
new Thread(new Task<Void>() {
@Override
@Override
protected Void call()
protected Void call()
{
{
try
try
{
{
boolean result = serverListener.onNormalActionClicked(normalAction);
boolean result = serverListener.onNormalActionClicked(normalAction);
if(!result)
if(!result)
{
{
sendActionFailed(profileID, actionID);
sendActionFailed(profileID, actionID);
}
}
}
}
catch (SevereException e)
catch (SevereException e)
{
{
exceptionAndAlertHandler.handleSevereException(e);
exceptionAndAlertHandler.handleSevereException(e);
}
}
return null;
return null;
}
}
}).start();
}).start();
}
}
} catch (Exception e) {
} catch (Exception e) {
e.printStackTrace();
e.printStackTrace();
exceptionAndAlertHandler.handleMinorException(new MinorException(e.getMessage()));
exceptionAndAlertHandler.handleMinorException(new MinorException(e.getMessage()));
}
}
}
}
public void sendActionFailed(String profileID, String actionID) throws SevereException {
public void sendActionFailed(String profileID, String actionID) throws SevereException {
logger.info("Sending failed status ...");
logger.info("Sending failed status ...");
writeToStream("action_failed::"+
writeToStream("action_failed::"+
profileID+"::"+
profileID+"::"+
actionID+"::");
actionID+"::");
}
}
}
}
/*
/*
Main.java
Stream-Pi - Free & Open-Source Modular Cross-Platform Programmable Macropad
Copyright (C) 2019-2021 Debayan Sutradhar (rnayabed), Samuel Quiñones (SamuelQuinones)
First class started when the app runs.
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Written by Debayan Sutradhar (@rnayabed)
Written by : Debayan Sutradhar (rnayabed)
*/
*/
package com.StreamPi.Server;
package com.StreamPi.Server;
import com.StreamPi.Server.Controller.Controller;
import com.StreamPi.Server.Controller.Controller;
import com.StreamPi.Server.Info.ServerInfo;
import com.StreamPi.Server.Info.ServerInfo;
import javafx.application.Application;
import javafx.application.Application;
import javafx.application.HostServices;
import javafx.scene.Scene;
import javafx.scene.Scene;
import javafx.scene.image.Image;
import javafx.stage.Stage;
import javafx.stage.Stage;
public class Main extends Application {
public class Main extends Application {
public void start(Stage stage) {
Controller d = new Controller(); //Starts new dash instance
Scene s = new Scene(d); //Starts new scene instance from dash
/**
stage.setScene(s); //Init Scene
* First method to be called
d.setHostServices(getHostServices());
* This method first parses all the available command line arguments passed.
d.init();
* Then a new instance of Controller is created, and then initialised.
}
*/
public void start(Stage stage) {
public static void main(String[] args)
for(String eachArg : getParameters().getRaw())
{
for(String eachArg : args)
{
{
String[] r = eachArg.split("=");
String[] r = eachArg.split("=");
if(r[0].equals("-DStreamPi.startupRunnerFileName"))
if(r[0].equals("-DStreamPi.startupRunnerFileName"))
ServerInfo.getInstance().setRunnerFileName(r[1]);
ServerInfo.getInstance().setRunnerFileName(r[1]);
else if(r[0].equals("-DStreamPi.startupMode"))
else if(r[0].equals("-DStreamPi.startupMode"))
ServerInfo.getInstance().setStartMinimised(r[1].equals("min"));
ServerInfo.getInstance().setStartMinimised(r[1].equals("min"));
}
}
Controller d = new Controller();
Scene s = new Scene(d);
stage.setScene(s);
d.setHostServices(getHostServices());
d.init();
}
/**
* This is a fallback. Called in some JVMs.
* This method just sends the command line arguments to JavaFX Application
*/
public static void main(String[] args)
{
launch(args);
launch(args);
}
}
}
}