From fd781afb1888aafdce0ed5fdb69bb957feaf8710 Mon Sep 17 00:00:00 2001 From: sirjonasxx <36828922+sirjonasxx@users.noreply.github.com> Date: Sun, 24 Jun 2018 01:21:53 +0200 Subject: [PATCH] extension suppoer & abstract Extension class implemented, not tested yet. --- src/main/Main.java | 2 + src/main/extensions/Extension.java | 210 ++++++++++++++++++ src/main/protocol/HMessage.java | 50 ++++- src/main/protocol/HPacket.java | 26 ++- src/main/ui/extensions/Extensions.java | 165 +++++++++++++- src/main/ui/extensions/GEarthExtension.java | 169 ++++++++++++++ .../extensions/GEarthExtensionsRegistrer.java | 35 +++ .../ExtensionFilesManager.java | 19 ++ .../ExtensionFilesManagerFactory.java | 7 + .../LinuxExtensionFilesManager.java | 27 +++ .../extensionfile/ExtensionFile.java | 10 + 11 files changed, 714 insertions(+), 6 deletions(-) create mode 100644 src/main/extensions/Extension.java create mode 100644 src/main/ui/extensions/GEarthExtension.java create mode 100644 src/main/ui/extensions/GEarthExtensionsRegistrer.java create mode 100644 src/main/ui/extensions/extensionfilemanager/ExtensionFilesManager.java create mode 100644 src/main/ui/extensions/extensionfilemanager/ExtensionFilesManagerFactory.java create mode 100644 src/main/ui/extensions/extensionfilemanager/LinuxExtensionFilesManager.java create mode 100644 src/main/ui/extensions/extensionfilemanager/extensionfile/ExtensionFile.java diff --git a/src/main/Main.java b/src/main/Main.java index 03cb07b..62a8940 100644 --- a/src/main/Main.java +++ b/src/main/Main.java @@ -38,8 +38,10 @@ public class Main extends Application { } + public static String[] args; public static void main(String[] args) { + Main.args = args; launch(args); } } diff --git a/src/main/extensions/Extension.java b/src/main/extensions/Extension.java new file mode 100644 index 0000000..628086b --- /dev/null +++ b/src/main/extensions/Extension.java @@ -0,0 +1,210 @@ +package main.extensions; + +import main.protocol.HMessage; +import main.protocol.HPacket; +import main.protocol.packethandler.PayloadBuffer; +import main.ui.extensions.Extensions; + +import java.io.IOException; +import java.io.InputStream; +import java.io.OutputStream; +import java.net.Socket; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +/** + * Created by Jonas on 23/06/18. + */ +public abstract class Extension { + + public interface MessageListener { + void act(HMessage message); + } + public interface FlagsCheckListener { + void act(String[] args); + } + + + private static final String[] PORT_FLAG = {"--port", "-p"}; + + private OutputStream out = null; + private Map> incomingMessageListeners = new HashMap<>(); + private Map> outgoingMessageListeners = new HashMap<>(); + private FlagsCheckListener flagRequestCallback = null; + + + + public Extension(String[] args) { + //obtain port + int port = 0; + + outerloop: + for (int i = 0; i < args.length - 1; i++) { + for (String str : PORT_FLAG) { + if (args[i].equals(str)) { + port = Integer.parseInt(args[i+1]); + break outerloop; + } + } + } + + + try { + Socket GEarthExtensionServer = new Socket("localhost", port); + + InputStream in = GEarthExtensionServer.getInputStream(); + out = GEarthExtensionServer.getOutputStream(); + + PayloadBuffer buffer = new PayloadBuffer(); + while (!GEarthExtensionServer.isClosed()) { + if (in.available() > 0) { + byte[] data = new byte[in.available()]; + in.read(data); + buffer.push(data); + + HPacket[] packets = buffer.receive(); + for (HPacket packet : packets) { + if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.INFOREQUEST) { + HPacket response = new HPacket(Extensions.INCOMING_MESSAGES_IDS.EXTENSIONINFO); + response.appendString(getTitle()) + .appendString(getAuthor()) + .appendString(getVersion()) + .appendString(getDescription()); + writeToStream(response.toBytes()); + } + else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.CONNECTIONSTART) { + onStartConnection(); + } + else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.CONNECTIONEND) { + onEndConnection(); + } + else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.FLAGSCHECK) { + // body = an array of G-Earths main flags + if (flagRequestCallback != null) { + int arraysize = packet.readInteger(); + String[] gEarthArgs = new String[arraysize]; + for (int i = 0; i < gEarthArgs.length; i++) { + gEarthArgs[i] = packet.readString(); + } + flagRequestCallback.act(gEarthArgs); + } + flagRequestCallback = null; + } + else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.INIT) { + init(); + } + else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.FREEFLOW) { + // nothing to be done yet + } + else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.ONDOUBLECLICK) { + onDoubleClick(); + } + else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.PACKETINTERCEPT) { + HMessage habboMessage = new HMessage(packet.readString()); + HPacket habboPacket = habboMessage.getPacket(); + + Map> listeners = + habboMessage.getDestination() == HMessage.Side.TOCLIENT ? + incomingMessageListeners : + outgoingMessageListeners; + + if (listeners.containsKey(-1)) { // registered on all packets + for (int i = listeners.get(-1).size() - 1; i >= 0; i--) { + listeners.get(-1).get(i).act(habboMessage); + } + } + if (listeners.containsKey(habboPacket.headerId())) { + for (int i = listeners.get(habboPacket.headerId()).size() - 1; i >= 0; i--) { + listeners.get(habboPacket.headerId()).get(i).act(habboMessage); + } + } + + HPacket response = new HPacket(Extensions.INCOMING_MESSAGES_IDS.MANIPULATEDPACKET); + response.appendString(habboMessage.stringify()); + + writeToStream(response.toBytes()); + } + } + } + Thread.sleep(1); + } + + + } catch (IOException | InterruptedException e) { + e.printStackTrace(); + } + } + + private void writeToStream(byte[] bytes) throws IOException { + synchronized (out) { + out.write(bytes); + out.flush(); + } + } + + //methods returns if succeed + protected boolean sendToClient(HPacket packet) { + return send(packet, HMessage.Side.TOCLIENT); + } + protected boolean sendToServer(HPacket packet) { + return send(packet, HMessage.Side.TOSERVER); + } + private boolean send(HPacket packet, HMessage.Side side) { + HPacket packet1 = new HPacket(Extensions.INCOMING_MESSAGES_IDS.SENDMESSAGE); + packet1.appendByte(side == HMessage.Side.TOCLIENT ? (byte)0 : (byte)1); + packet1.appendInt(packet.getBytesLength()); + packet1.appendBytes(packet.toBytes()); + try { + writeToStream(packet1.toBytes()); + return true; + } catch (IOException e) { + return false; + } + } + + protected void intercept(HMessage.Side side, int headerId, MessageListener messageListener) { + Map> listeners = + side == HMessage.Side.TOCLIENT ? + incomingMessageListeners : + outgoingMessageListeners; + + if (!listeners.containsKey(headerId)) { + listeners.put(headerId, new ArrayList<>()); + } + + listeners.get(headerId).add(messageListener); + } + protected void intercept(HMessage.Side side, MessageListener messageListener) { + intercept(side, -1, messageListener); + } + + //returns "false" if another flag requester was busy + protected boolean requestFlags(FlagsCheckListener flagRequestCallback) { + if (this.flagRequestCallback != null) return false; + this.flagRequestCallback = flagRequestCallback; + return true; + } + + protected void writeToConsole(String s) { + HPacket packet = new HPacket(Extensions.INCOMING_MESSAGES_IDS.EXTENSIONCONSOLELOG); + packet.appendString(s); + try { + writeToStream(packet.toBytes()); + } catch (IOException e) { + e.printStackTrace(); + } + } + + // All methods under here block the stream, use threads if needed. + protected abstract void init(); + protected abstract void onDoubleClick(); + protected abstract void onStartConnection(); + protected abstract void onEndConnection(); + + protected abstract String getTitle(); + protected abstract String getDescription(); + protected abstract String getVersion(); + protected abstract String getAuthor(); +} diff --git a/src/main/protocol/HMessage.java b/src/main/protocol/HMessage.java index b4a3127..56cc384 100644 --- a/src/main/protocol/HMessage.java +++ b/src/main/protocol/HMessage.java @@ -1,6 +1,8 @@ package main.protocol; -public class HMessage { +import main.misc.StringifyAble; + +public class HMessage implements StringifyAble { public enum Side { TOSERVER, @@ -13,6 +15,9 @@ public class HMessage { private boolean isBlocked; + public HMessage(String fromString) { + constructFromString(fromString); + } public HMessage(HPacket packet, Side side, int index) { this.side = side; @@ -42,4 +47,47 @@ public class HMessage { public boolean isCorrupted() { return hPacket.isCorrupted(); } + + + @Override + public String stringify() { + String s = (isBlocked ? "1" : "0") + "\t" + index + "\t" + side.name() + "\t" + hPacket.stringify(); + return s; + } + + @Override + public void constructFromString(String str) { + String[] parts = str.split("\t"); + this.isBlocked = parts[0].equals("1"); + this.index = Integer.parseInt(parts[1]); + this.side = parts[2].equals("TOCLIENT") ? Side.TOCLIENT : Side.TOSERVER; + HPacket p = new HPacket(new byte[0]); + p.constructFromString(parts[3]); + this.hPacket = p; + } + + @Override + public boolean equals(Object obj) { + if (!(obj instanceof HMessage)) return false; + + HMessage message = (HMessage) obj; + + return message.hPacket.equals(hPacket) && (side == message.side) && (index == message.index); + } + +// public static void main(String[] args) { +// HPacket packet3 = new HPacket(81, new byte[]{0,0,0,1,0,0}); +// +// HPacket packet = new HPacket(82, new byte[]{0,0,0,1,0,0}); +// HMessage message = new HMessage(packet, Side.TOSERVER, 5); +// +// String stringed = message.stringify(); +// +// HMessage message2 = new HMessage(stringed); +// HPacket packet1 = message2.getPacket(); +// +// System.out.println(message.equals(message2)); +// System.out.println(packet.equals(packet1)); +// System.out.println(packet.equals(packet3)); +// } } diff --git a/src/main/protocol/HPacket.java b/src/main/protocol/HPacket.java index f536a55..2675b0c 100644 --- a/src/main/protocol/HPacket.java +++ b/src/main/protocol/HPacket.java @@ -1,5 +1,7 @@ package main.protocol; +import main.misc.StringifyAble; + import java.io.UnsupportedEncodingException; import java.nio.ByteBuffer; import java.nio.charset.StandardCharsets; @@ -8,7 +10,7 @@ import java.util.Arrays; import java.util.HashSet; import java.util.Set; -public class HPacket { +public class HPacket implements StringifyAble { // te komen: toExpressions (+impl. expressies) private boolean isEdited = false; private byte[] packetInBytes; @@ -403,7 +405,6 @@ public class HPacket { } public HPacket replaceAllString(String oldS, String newS) { while (replaceFirstString(oldS, newS)) {} - return this; } @@ -737,7 +738,7 @@ public class HPacket { resultTest[j] = "{b:"+(packetInBytes[j] == 1 ? "true" : "false")+"}"; } else { - resultTest[j] = "{b:"+packetInBytes[j]+"}"; + resultTest[j] = "{b:"+((((int)packetInBytes[j])+256)%256)+"}"; } } opeenvolging = 0; @@ -761,4 +762,23 @@ public class HPacket { return expression.toString().replace("{i:0}{b:false}{b:true}", "{s:}{i:1}"); } + @Override + public String stringify() { + String st = (isEdited ? "1" : "0") + this.toString(); + return st; + } + + @Override + public void constructFromString(String str) { + this.isEdited = str.charAt(0) == '1'; + packetInBytes = fromStringToBytes(str.substring(1)); + } + + @Override + public boolean equals(Object object) { + if (!(object instanceof HPacket)) return false; + + HPacket packet2 = (HPacket) object; + return Arrays.equals(packetInBytes, packet2.packetInBytes) && (isEdited == packet2.isEdited); + } } \ No newline at end of file diff --git a/src/main/ui/extensions/Extensions.java b/src/main/ui/extensions/Extensions.java index 80942ce..1b9763d 100644 --- a/src/main/ui/extensions/Extensions.java +++ b/src/main/ui/extensions/Extensions.java @@ -1,7 +1,13 @@ package main.ui.extensions; +import main.Main; +import main.protocol.*; import main.ui.SubForm; +import java.io.IOException; +import java.net.ServerSocket; +import java.util.*; + /** * Created by Jonas on 06/04/18. */ @@ -47,7 +53,7 @@ import main.ui.SubForm; * | | | exact implementation is found in the Java abstract Extension class | * ----------------------------------------------------------------------------------------------------- * | 3 | PACKET-INTERCEPT* | Includes the whole HMessage as body, needs response with the | - * | | | manipulated HMessage (OUTGOING id: 2) (blank body = no manipulation) | + * | | | manipulated HMessage (OUTGOING id: 2) | * ----------------------------------------------------------------------------------------------------- * | 4 | FLAGS-CHECK** | Body: String with G-Earth's boot flags (args from static main method) | * ----------------------------------------------------------------------------------------------------- @@ -55,6 +61,10 @@ import main.ui.SubForm; * | | | you could check this yourself as well (listen to out:4000 packet) | * ----------------------------------------------------------------------------------------------------- * | 6 | CONNECTION END | Empty body, just a note that a connection has ended | +* ----------------------------------------------------------------------------------------------------- + * | 7 | INIT | Empty body, a connection with G-Earth has been set up | + * ----------------------------------------------------------------------------------------------------- + * | 99 | FREE FLOW | extension-specific body | * ----------------------------------------------------------------------------------------------------- * * OUTGOING MESSAGES: (marked with * if that is a response to one of the msgs above) @@ -70,17 +80,168 @@ import main.ui.SubForm; * | 4 | SEND-MESSAGE | Body: HMessage object. Sends the HPacket wrapped in the HMessage | * | | | to the client/server | * ----------------------------------------------------------------------------------------------------- + * | 99 | FREE FLOW | extension-specific body | + * ----------------------------------------------------------------------------------------------------- * * 4. Your extension will only appear in the extension list once the EXTENSION-INFO has been received by G-Earth * - * + * */ public class Extensions extends SubForm { + public static class OUTGOING_MESSAGES_IDS { + public static final int ONDOUBLECLICK = 1; + public static final int INFOREQUEST = 2; // backend: implemented + public static final int PACKETINTERCEPT = 3; // backend: implemented + public static final int FLAGSCHECK = 4; // backend: implemented + public static final int CONNECTIONSTART = 5; // backend: implemented + public static final int CONNECTIONEND = 6; // backend: implemented + public static final int INIT = 7; // backend: implemented + public static final int FREEFLOW = 99; // no implementation needed yet + } + + + public static class INCOMING_MESSAGES_IDS { + public static final int EXTENSIONINFO = 1; // backend: implemented + public static final int MANIPULATEDPACKET = 2; // backend: implemented + public static final int REQUESTFLAGS = 3; // backend: implemented + public static final int SENDMESSAGE = 4; // backend: implemented + public static final int EXTENSIONCONSOLELOG = 98; + public static final int FREEFLOW = 99; // no implementation needed yet + } + + + + private List gEarthExtensions = new ArrayList<>(); + public void initialize() { } + protected void onParentSet() { + getHConnection().addStateChangeListener((oldState, newState) -> { + if (newState == HConnection.State.CONNECTED) { + for (GEarthExtension extension : gEarthExtensions) { + extension.sendMessage(new HPacket(OUTGOING_MESSAGES_IDS.CONNECTIONSTART)); + } + } + if (oldState == HConnection.State.CONNECTED) { + for (GEarthExtension extension : gEarthExtensions) { + extension.sendMessage(new HPacket(OUTGOING_MESSAGES_IDS.CONNECTIONEND)); + } + } + }); + + getHConnection().addTrafficListener(1, message -> { + Set collection = new HashSet<>(gEarthExtensions); + + String stringified = message.stringify(); + HPacket manipulatePacketRequest = new HPacket(OUTGOING_MESSAGES_IDS.PACKETINTERCEPT); + manipulatePacketRequest.appendString(stringified); + + boolean[] isblock = new boolean[1]; + + for (GEarthExtension extension : gEarthExtensions) { + GEarthExtension.ReceiveMessageListener respondCallback = new GEarthExtension.ReceiveMessageListener() { + @Override + public void act(HPacket packet) { + if (packet.headerId() == INCOMING_MESSAGES_IDS.MANIPULATEDPACKET) { + String stringifiedresponse = packet.readString(); + HMessage responseMessage = new HMessage(stringifiedresponse); + if (responseMessage.getDestination() == message.getDestination() && responseMessage.getIndex() == message.getIndex()) { + if (!message.equals(responseMessage)) { + message.constructFromString(stringifiedresponse); + if (responseMessage.isBlocked()) { + isblock[0] = true; + } + } + collection.remove(extension); + extension.removeOnReceiveMessageListener(this); + } + } + } + }; + extension.addOnReceiveMessageListener(respondCallback); + + extension.sendMessage(manipulatePacketRequest); + } + + //block untill all extensions have responded + List willdelete = new ArrayList<>(); + while (!collection.isEmpty()) { + for (GEarthExtension extension : collection) { + if (!gEarthExtensions.contains(extension)) willdelete.add(extension); + } + for (int i = willdelete.size() - 1; i >= 0; i--) { + collection.remove(willdelete.get(i)); + willdelete.remove(i); + } + + try {Thread.sleep(1);} catch (InterruptedException e) {e.printStackTrace();} + } + + if (isblock[0]) { + message.setBlocked(true); + } + }); + + + GEarthExtensionsRegistrer extensionsRegistrer = null; + HashMap messageListeners = new HashMap<>(); + try { + extensionsRegistrer = new GEarthExtensionsRegistrer(new GEarthExtensionsRegistrer.ExtensionRegisterObserver() { + @Override + public void onConnect(GEarthExtension extension) { + gEarthExtensions.add(extension); + GEarthExtension.ReceiveMessageListener receiveMessageListener = message -> { + if (message.headerId() == INCOMING_MESSAGES_IDS.REQUESTFLAGS) { // no body + HPacket packet = new HPacket(OUTGOING_MESSAGES_IDS.FLAGSCHECK); + packet.appendInt(Main.args.length); + for (String arg : Main.args) { + packet.appendString(arg); + } + extension.sendMessage(packet); + } + else if (message.headerId() == INCOMING_MESSAGES_IDS.SENDMESSAGE) { + Byte side = message.readByte(); + int byteLength = message.readInteger(); + byte[] packetAsByteArray = message.readBytes(byteLength); + + HPacket packet = new HPacket(packetAsByteArray); + if (!packet.isCorrupted()) { + if (side == 0) { // toclient + getHConnection().sendToClientAsync(packet); + } + else if (side == 1) { // toserver + getHConnection().sendToServerAsync(packet); + } + } + } + }; + messageListeners.put(extension, receiveMessageListener); + extension.addOnReceiveMessageListener(receiveMessageListener); + + extension.sendMessage(new HPacket(OUTGOING_MESSAGES_IDS.INIT)); + if (getHConnection().getState() == HConnection.State.CONNECTED) { + extension.sendMessage(new HPacket(OUTGOING_MESSAGES_IDS.CONNECTIONSTART)); + } + } + + @Override + public void onDisconnect(GEarthExtension extension) { + gEarthExtensions.remove(extension); + + extension.removeOnReceiveMessageListener(messageListeners.get(extension)); + messageListeners.remove(extension); + } + }); + } catch (IOException e) { + e.printStackTrace(); + } + System.out.println("Extension server registered on port: " + extensionsRegistrer.getPort()); + + } + } diff --git a/src/main/ui/extensions/GEarthExtension.java b/src/main/ui/extensions/GEarthExtension.java new file mode 100644 index 0000000..21518fc --- /dev/null +++ b/src/main/ui/extensions/GEarthExtension.java @@ -0,0 +1,169 @@ +package main.ui.extensions; + +import main.protocol.HMessage; +import main.protocol.HPacket; +import main.protocol.packethandler.PayloadBuffer; + +import java.io.IOException; +import java.io.InputStream; +import java.net.Socket; +import java.util.ArrayList; +import java.util.List; + +/** + * Created by Jonas on 21/06/18. + */ +public class GEarthExtension { + + private String title; + private String author; + private String version; + private String description; + + private Socket connection; + + //calls callback when the extension is creatd + static void create(Socket connection, OnCreatedCallback callback, OnDisconnectedCallback onDisconnectedCallback) { + + new Thread(() -> { + try { + connection.getOutputStream().write((new HPacket(Extensions.OUTGOING_MESSAGES_IDS.INFOREQUEST)).toBytes()); + connection.getOutputStream().flush(); + + PayloadBuffer payloadBuffer = new PayloadBuffer(); + InputStream inputStream = connection.getInputStream(); + + outerloop: + while (!connection.isClosed()) { + if (inputStream.available() > 0) { + byte[] incoming = new byte[inputStream.available()]; + inputStream.read(incoming); + payloadBuffer.push(incoming); + } + + HPacket[] hPackets = payloadBuffer.receive(); + for (HPacket packet : hPackets) { // it should be only one packet + if (packet.headerId() == Extensions.INCOMING_MESSAGES_IDS.EXTENSIONINFO) { + + GEarthExtension gEarthExtension = new GEarthExtension( + packet.readString(), + packet.readString(), + packet.readString(), + packet.readString(), + connection, + onDisconnectedCallback + ); + callback.act(gEarthExtension); + + break outerloop; + } + } + + Thread.sleep(1); + } + + } catch (IOException | InterruptedException ignored) {} + }).start(); + + } + + private GEarthExtension(String title, String author, String version, String description, Socket connection, OnDisconnectedCallback onDisconnectedCallback) { + this.title = title; + this.author = author; + this.version = version; + this.description = description; + this.connection = connection; + + GEarthExtension selff = this; + new Thread(() -> { + try { + PayloadBuffer payloadBuffer = new PayloadBuffer(); + InputStream inputStream = connection.getInputStream(); + + while (!connection.isClosed()) { + if (inputStream.available() > 0) { + byte[] incoming = new byte[inputStream.available()]; + inputStream.read(incoming); + payloadBuffer.push(incoming); + } + + HPacket[] hPackets = payloadBuffer.receive(); + for (HPacket packet : hPackets) { + for (int i = receiveMessageListeners.size() - 1; i >= 0; i--) { + receiveMessageListeners.get(i).act(packet); + } + } + + Thread.sleep(1); + } + onDisconnectedCallback.act(selff); + + } catch (IOException | InterruptedException e) { + e.printStackTrace(); + } + }).start(); + + + } + + public Socket getConnection() { + return connection; + } + + public String getAuthor() { + return author; + } + + public String getDescription() { + return description; + } + + public String getTitle() { + return title; + } + + public String getVersion() { + return version; + } + + + + public boolean closeConnection() { + try { + connection.close(); + return true; + } catch (IOException e) { + return false; + } + } + + public boolean sendMessage(HPacket message) { + try { + connection.getOutputStream().write(message.toBytes()); + connection.getOutputStream().flush(); + return true; + } catch (IOException e) { + return false; + } + } + + + private List receiveMessageListeners = new ArrayList<>(); + public void addOnReceiveMessageListener(ReceiveMessageListener receiveMessageListener) { + receiveMessageListeners.add(receiveMessageListener); + } + public void removeOnReceiveMessageListener(ReceiveMessageListener receiveMessageListener) { + receiveMessageListeners.remove(receiveMessageListener); + } + + public interface ReceiveMessageListener { + void act(HPacket message); + } + public interface OnCreatedCallback { + void act(GEarthExtension extension); // returns itself + } + public interface OnDisconnectedCallback { + void act(GEarthExtension extension); // returns itself + } + +} \ No newline at end of file diff --git a/src/main/ui/extensions/GEarthExtensionsRegistrer.java b/src/main/ui/extensions/GEarthExtensionsRegistrer.java new file mode 100644 index 0000000..f9938e3 --- /dev/null +++ b/src/main/ui/extensions/GEarthExtensionsRegistrer.java @@ -0,0 +1,35 @@ +package main.ui.extensions; + +import java.io.IOException; +import java.net.ServerSocket; +import java.net.Socket; + +/** + * Created by Jonas on 21/06/18. + */ +public class GEarthExtensionsRegistrer { + + final ServerSocket serverSocket; + + GEarthExtensionsRegistrer(ExtensionRegisterObserver observer) throws IOException { + + serverSocket = new ServerSocket(0); + new Thread(() -> { + try { + while (!serverSocket.isClosed()) { + Socket extensionSocket = serverSocket.accept(); + GEarthExtension.create(extensionSocket, observer::onConnect, observer::onDisconnect); + } + } catch (IOException e) {e.printStackTrace();} + }).start(); + } + + public int getPort() { + return serverSocket.getLocalPort(); + } + + public interface ExtensionRegisterObserver { + void onConnect(GEarthExtension extension); + void onDisconnect(GEarthExtension extension); + } +} diff --git a/src/main/ui/extensions/extensionfilemanager/ExtensionFilesManager.java b/src/main/ui/extensions/extensionfilemanager/ExtensionFilesManager.java new file mode 100644 index 0000000..b9473e4 --- /dev/null +++ b/src/main/ui/extensions/extensionfilemanager/ExtensionFilesManager.java @@ -0,0 +1,19 @@ +package main.ui.extensions.extensionfilemanager; + +import main.ui.extensions.extensionfilemanager.extensionfile.ExtensionFile; + +import java.io.File; +import java.util.List; + +/** + * Created by Jonas on 21/06/18. + */ +public interface ExtensionFilesManager { + + List getAllExtensions(); + + ExtensionFile addExtension(File file); //returns g-earth extension file, returns null if failure + + boolean removeExtension(ExtensionFile file); //returns false if not done + +} diff --git a/src/main/ui/extensions/extensionfilemanager/ExtensionFilesManagerFactory.java b/src/main/ui/extensions/extensionfilemanager/ExtensionFilesManagerFactory.java new file mode 100644 index 0000000..c9e0483 --- /dev/null +++ b/src/main/ui/extensions/extensionfilemanager/ExtensionFilesManagerFactory.java @@ -0,0 +1,7 @@ +package main.ui.extensions.extensionfilemanager; + +/** + * Created by Jonas on 21/06/18. + */ +public class ExtensionFilesManagerFactory { +} diff --git a/src/main/ui/extensions/extensionfilemanager/LinuxExtensionFilesManager.java b/src/main/ui/extensions/extensionfilemanager/LinuxExtensionFilesManager.java new file mode 100644 index 0000000..2ee1a5c --- /dev/null +++ b/src/main/ui/extensions/extensionfilemanager/LinuxExtensionFilesManager.java @@ -0,0 +1,27 @@ +package main.ui.extensions.extensionfilemanager; + +import main.ui.extensions.extensionfilemanager.extensionfile.ExtensionFile; + +import java.io.File; +import java.util.List; + +/** + * Created by Jonas on 21/06/18. + */ +public class LinuxExtensionFilesManager implements ExtensionFilesManager { + + @Override + public List getAllExtensions() { + return null; + } + + @Override + public ExtensionFile addExtension(File file) { + return null; + } + + @Override + public boolean removeExtension(ExtensionFile file) { + return false; + } +} diff --git a/src/main/ui/extensions/extensionfilemanager/extensionfile/ExtensionFile.java b/src/main/ui/extensions/extensionfilemanager/extensionfile/ExtensionFile.java new file mode 100644 index 0000000..4e3524c --- /dev/null +++ b/src/main/ui/extensions/extensionfilemanager/extensionfile/ExtensionFile.java @@ -0,0 +1,10 @@ +package main.ui.extensions.extensionfilemanager.extensionfile; + +/** + * Created by Jonas on 21/06/18. + */ +public class ExtensionFile { + + + +}