hashing in Logger & example extension

This commit is contained in:
sirjonasxx 2018-11-17 19:08:54 +01:00
parent d14b21af62
commit c130058694
16 changed files with 173 additions and 72 deletions

View File

@ -26,7 +26,7 @@ public class AdminOnConnect extends Extension {
private boolean done = true; private boolean done = true;
protected void init() { protected void initExtension() {
intercept(HMessage.Side.TOCLIENT, message -> { intercept(HMessage.Side.TOCLIENT, message -> {
if (!done) { if (!done) {
HPacket packet = message.getPacket(); HPacket packet = message.getPacket();

View File

@ -40,7 +40,7 @@
<manifest> <manifest>
<addDefaultImplementationEntries>true</addDefaultImplementationEntries> <addDefaultImplementationEntries>true</addDefaultImplementationEntries>
<addClasspath>true</addClasspath> <addClasspath>true</addClasspath>
<mainClass>extensions.speechcolorizer.SpeechColorizer</mainClass> <mainClass>extensions.happyspeech.HappySpeech</mainClass>
<useUniqueVersions>false</useUniqueVersions> <useUniqueVersions>false</useUniqueVersions>
<classpathPrefix>lib/</classpathPrefix> <classpathPrefix>lib/</classpathPrefix>
<addDefaultImplementationEntries>true</addDefaultImplementationEntries> <addDefaultImplementationEntries>true</addDefaultImplementationEntries>
@ -65,7 +65,7 @@
<outputDirectory>${project.build.directory}/bin</outputDirectory> <outputDirectory>${project.build.directory}/bin</outputDirectory>
<archive> <archive>
<manifest> <manifest>
<mainClass>extensions.speechcolorizer.SpeechColorizer</mainClass> <mainClass>extensions.happyspeech.HappySpeech</mainClass>
</manifest> </manifest>
</archive> </archive>
<descriptorRefs> <descriptorRefs>

View File

@ -1,7 +1,8 @@
package extensions.speechcolorizer; package extensions.happyspeech;
import gearth.extensions.Extension; import gearth.extensions.Extension;
import gearth.extensions.ExtensionInfo; import gearth.extensions.ExtensionInfo;
import gearth.extensions.extra.hashing.HashSupport;
import gearth.protocol.HMessage; import gearth.protocol.HMessage;
import gearth.protocol.HPacket; import gearth.protocol.HPacket;
@ -16,50 +17,43 @@ import java.util.Random;
*/ */
@ExtensionInfo( @ExtensionInfo(
Title = "Colorize me!", Title = "HappySpeech",
Description = "Because we like to be weird", Description = "Example extension for hashSupport",
Version = "1.0", Version = "1.0",
Author = "sirjonasxx" Author = "sirjonasxx"
) )
public class SpeechColorizer extends Extension { public class HappySpeech extends Extension {
public static void main(String[] args) { public static void main(String[] args) {
new SpeechColorizer(args).run(); new HappySpeech(args).run();
} }
private SpeechColorizer(String[] args) { private HappySpeech(String[] args) {
super(args); super(args);
} }
private static final int SPEECH_ID = 3373;
private static final String[] COLORS = {"red", "blue", "cyan", "green", "purple"}; private static final String[] COLORS = {"red", "blue", "cyan", "green", "purple"};
private static final Random r = new Random(); private static final Random r = new Random();
private HashSupport hashSupport;
@Override @Override
protected void init() { protected void initExtension() {
intercept(HMessage.Side.TOSERVER, SPEECH_ID, this::onSendMessage); hashSupport = new HashSupport(this);
System.out.println("test"); hashSupport.intercept(HMessage.Side.TOSERVER, "RoomUserShout", this::onSendMessage);
hashSupport.intercept(HMessage.Side.TOSERVER, "RoomUserTalk", this::onSendMessage);
} }
private void onSendMessage(HMessage message) { private void onSendMessage(HMessage message) {
HPacket packet = message.getPacket(); HPacket packet = message.getPacket();
String speechtext = packet.readString(); String speechtext = packet.readString();
System.out.println("you said: " + speechtext);
message.setBlocked(speechtext.equals("blocked")); message.setBlocked(speechtext.equals("blocked"));
packet.replaceString(6, "@" + COLORS[r.nextInt(COLORS.length)] + "@" + speechtext); packet.replaceString(6, "@" + COLORS[r.nextInt(COLORS.length)] + "@" + speechtext + " :)");
} }
protected String getTitle() { protected void onClick() {
return "Colorize me!"; //{l}{u:1047}{i:0}{s:text}{i:0}{i:0}{i:0}{i:0}
} hashSupport.sendToClient("RoomUserTalk", 0, "You clicked on this extension!", 0, 0, 0, 0);
protected String getDescription() {
return "Because we like to be weird";
}
protected String getVersion() {
return "1.0";
}
protected String getAuthor() {
return "sirjonasxx";
} }
} }

View File

@ -60,7 +60,8 @@
<descriptorRefs> <descriptorRefs>
<descriptorRef>jar-with-dependencies</descriptorRef> <descriptorRef>jar-with-dependencies</descriptorRef>
</descriptorRefs> </descriptorRefs>
<finalName>G-Earth-${project.version}</finalName> <!--<finalName>G-Earth-${project.version}</finalName>-->
<finalName>G-Earth</finalName>
<appendAssemblyId>false</appendAssemblyId> <appendAssemblyId>false</appendAssemblyId>
</configuration> </configuration>
</plugin> </plugin>

View File

@ -156,7 +156,7 @@ public abstract class Extension implements IExtension{
flagRequestCallback = null; flagRequestCallback = null;
} }
else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.INIT) { else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.INIT) {
init(); initExtension();
} }
else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.FREEFLOW) { else if (packet.headerId() == Extensions.OUTGOING_MESSAGES_IDS.FREEFLOW) {
// nothing to be done yet // nothing to be done yet
@ -338,7 +338,7 @@ public abstract class Extension implements IExtension{
* Gets called when a connection has been established with G-Earth. * Gets called when a connection has been established with G-Earth.
* This does not imply a connection with Habbo is setup. * This does not imply a connection with Habbo is setup.
*/ */
protected void init(){} protected void initExtension(){}
/** /**
* The application got doubleclicked from the G-Earth interface. Doing something here is optional * The application got doubleclicked from the G-Earth interface. Doing something here is optional

View File

@ -21,7 +21,7 @@ public class ExtensionFormLauncher extends Application{
extensionForm.extension = new Extension(args) { extensionForm.extension = new Extension(args) {
@Override @Override
protected void init() { protected void initExtension() {
extensionForm.initExtension(); extensionForm.initExtension();
} }

View File

@ -27,7 +27,7 @@ public class HarbleAPI {
this.destination = destination; this.destination = destination;
this.headerId = headerId; this.headerId = headerId;
this.hash = hash; this.hash = hash;
this.name = name; this.name = (name == null || name.equals("null") ? null : name);
} }
public String getName() { public String getName() {
return name; return name;
@ -41,6 +41,11 @@ public class HarbleAPI {
public String getHash() { public String getHash() {
return hash; return hash;
} }
public String toString() {
String s = (headerId+": " + "["+hash+"]" + "["+name+"]");
return s;
}
} }
private Map<Integer, HarbleMessage> headerIdToMessage_incoming = new HashMap<>(); private Map<Integer, HarbleMessage> headerIdToMessage_incoming = new HashMap<>();
@ -52,13 +57,25 @@ public class HarbleAPI {
private Map<String, HarbleMessage> nameToMessage_incoming = new HashMap<>(); private Map<String, HarbleMessage> nameToMessage_incoming = new HashMap<>();
private Map<String, HarbleMessage> nameToMessage_outgoing = new HashMap<>(); private Map<String, HarbleMessage> nameToMessage_outgoing = new HashMap<>();
private boolean success = false;
/** /**
* cache file must be generated first within G-Earth, inb4 20 extensions requesting it at the same time * cache file must be generated first within G-Earth, inb4 20 extensions requesting it at the same time
* @param hotelversion * @param hotelversion
*/ */
public static HarbleAPI get(String hotelversion) {
HarbleAPI wannabe = new HarbleAPI(hotelversion);
if (!wannabe.success) {
return null;
}
return wannabe;
}
public HarbleAPI (String hotelversion) { public HarbleAPI (String hotelversion) {
if (Cacher.cacheFileExists(HarbleAPIFetcher.CACHE_PREFIX + hotelversion)) { if (Cacher.cacheFileExists(HarbleAPIFetcher.CACHE_PREFIX + hotelversion)) {
JSONObject object = Cacher.getCacheContents(HarbleAPIFetcher.CACHE_PREFIX + hotelversion); JSONObject object = Cacher.getCacheContents(HarbleAPIFetcher.CACHE_PREFIX + hotelversion);
success = true;
parse(object); parse(object);
} }
} }
@ -87,30 +104,53 @@ public class HarbleAPI {
} }
} }
private void parse(JSONObject object) { private void parse(JSONObject object) {
try {
JSONObject incoming = object.getJSONObject("IncomingMessages"); JSONObject incoming = object.getJSONObject("IncomingMessages");
JSONObject outgoing = object.getJSONObject("OutgoingMessages"); JSONObject outgoing = object.getJSONObject("OutgoingMessages");
if (incoming != null && outgoing != null) { if (incoming != null && outgoing != null) {
for (String key : incoming.keySet()) { for (String key : incoming.keySet()) {
try {
JSONObject inMsg = incoming.getJSONObject(key); JSONObject inMsg = incoming.getJSONObject(key);
String name = inMsg.getString("Name"); String name;
try {
name = inMsg.getString("Name");
}
catch (Exception e) {
name = null;
}
String hash = inMsg.getString("Hash"); String hash = inMsg.getString("Hash");
Integer headerId = Integer.parseInt(key); Integer headerId = Integer.parseInt(key);
HarbleMessage message = new HarbleMessage(HMessage.Side.TOCLIENT, headerId, hash, name); HarbleMessage message = new HarbleMessage(HMessage.Side.TOCLIENT, headerId, hash, name);
addMessage(message); addMessage(message);
} }
catch( Exception e) {}
}
for (String key : outgoing.keySet()) { for (String key : outgoing.keySet()) {
JSONObject outMsg = incoming.getJSONObject(key); try {
String name = outMsg.getString("Name"); JSONObject outMsg = outgoing.getJSONObject(key);
String name;
try {
name = outMsg.getString("Name");
} catch (Exception e) {
name = null;
}
String hash = outMsg.getString("Hash"); String hash = outMsg.getString("Hash");
Integer headerId = Integer.parseInt(key); Integer headerId = Integer.parseInt(key);
HarbleMessage message = new HarbleMessage(HMessage.Side.TOSERVER, headerId, hash, name); HarbleMessage message = new HarbleMessage(HMessage.Side.TOSERVER, headerId, hash, name);
addMessage(message); addMessage(message);
} }
catch( Exception e) {}
} }
} }
}
catch (Exception e) {
success = false;
}
}
public HarbleMessage getHarbleMessageFromHeaderId(HMessage.Side side, int headerId) { public HarbleMessage getHarbleMessageFromHeaderId(HMessage.Side side, int headerId) {
Map<Integer, HarbleMessage> headerIdToMessage = Map<Integer, HarbleMessage> headerIdToMessage =

View File

@ -1,6 +1,7 @@
package gearth.misc.harble_api; package gearth.misc.harble_api;
import gearth.misc.Cacher; import gearth.misc.Cacher;
import gearth.protocol.HMessage;
import org.json.JSONObject; import org.json.JSONObject;
import org.jsoup.Connection; import org.jsoup.Connection;
import org.jsoup.Jsoup; import org.jsoup.Jsoup;
@ -16,11 +17,14 @@ public class HarbleAPIFetcher {
public static final String CACHE_PREFIX = "HARBLE_API-"; public static final String CACHE_PREFIX = "HARBLE_API-";
public static final String HARBLE_API_URL = "https://api.harble.net/revisions/$hotelversion$.json"; public static final String HARBLE_API_URL = "https://api.harble.net/revisions/$hotelversion$.json";
public static HarbleAPI fetch(String hotelversion) { //latest fetched
public static HarbleAPI HARBLEAPI = null;
public static void fetch(String hotelversion) {
String cacheName = CACHE_PREFIX + hotelversion; String cacheName = CACHE_PREFIX + hotelversion;
if (Cacher.cacheFileExists(cacheName)) { if (Cacher.cacheFileExists(cacheName)) {
return new HarbleAPI(hotelversion); HARBLEAPI = new HarbleAPI(hotelversion);
} }
else { else {
Connection connection = Jsoup.connect(HARBLE_API_URL.replace("$hotelversion$", hotelversion)).ignoreContentType(true); Connection connection = Jsoup.connect(HARBLE_API_URL.replace("$hotelversion$", hotelversion)).ignoreContentType(true);
@ -32,20 +36,23 @@ public class HarbleAPIFetcher {
s = s.substring(6, s.length() - 7); s = s.substring(6, s.length() - 7);
JSONObject object = new JSONObject(s); JSONObject object = new JSONObject(s);
Cacher.updateCache(object, cacheName); Cacher.updateCache(object, cacheName);
HARBLEAPI = new HarbleAPI(hotelversion);
return new HarbleAPI(hotelversion);
} }
else { else {
return null; HARBLEAPI = null;
} }
} catch (IOException e) { } catch (IOException e) {
return null; HARBLEAPI = null;
} }
} }
} }
public static void main(String[] args) { public static void main(String[] args) {
HarbleAPI api = fetch("PRODUCTION-201810171204-70166177"); fetch("PRODUCTION-201810171204-70166177");
HarbleAPI api = HARBLEAPI;
HarbleAPI.HarbleMessage haMessage = api.getHarbleMessageFromHeaderId(HMessage.Side.TOSERVER, 525);
System.out.println(haMessage);
} }
} }

View File

@ -1,5 +1,6 @@
package gearth.ui.extensions; package gearth.ui.extensions;
import gearth.misc.harble_api.HarbleAPIFetcher;
import javafx.application.Platform; import javafx.application.Platform;
import javafx.event.ActionEvent; import javafx.event.ActionEvent;
import javafx.scene.control.Button; import javafx.scene.control.Button;
@ -149,6 +150,7 @@ public class Extensions extends SubForm {
getHConnection().addStateChangeListener((oldState, newState) -> { getHConnection().addStateChangeListener((oldState, newState) -> {
if (newState == HConnection.State.CONNECTED) { if (newState == HConnection.State.CONNECTED) {
HarbleAPIFetcher.fetch(getHConnection().getHotelVersion());
synchronized (gEarthExtensions) { synchronized (gEarthExtensions) {
for (GEarthExtension extension : gEarthExtensions) { for (GEarthExtension extension : gEarthExtensions) {
extension.sendMessage( extension.sendMessage(

View File

@ -1,6 +1,5 @@
package gearth.ui.logger; package gearth.ui.logger;
import gearth.ui.logger.loggerdisplays.UiLogger;
import javafx.application.Platform; import javafx.application.Platform;
import javafx.event.ActionEvent; import javafx.event.ActionEvent;
import javafx.scene.control.Button; import javafx.scene.control.Button;

View File

@ -2,6 +2,7 @@ package gearth.ui.logger.loggerdisplays;
import gearth.Main; import gearth.Main;
import gearth.misc.OSValidator; import gearth.misc.OSValidator;
import gearth.ui.logger.loggerdisplays.uilogger.UiLogger;
/** /**
* Created by Jonas on 04/04/18. * Created by Jonas on 04/04/18.

View File

@ -0,0 +1,14 @@
package gearth.ui.logger.loggerdisplays.uilogger;
/**
* Created by Jonas on 17/11/2018.
*/
class Element {
final String text;
final String className;
Element(String text, String className) {
this.text = text;
this.className = className;
}
}

View File

@ -1,7 +1,7 @@
package gearth.ui.logger.loggerdisplays; package gearth.ui.logger.loggerdisplays.uilogger;
import gearth.protocol.HPacket; import gearth.protocol.HPacket;
import gearth.ui.UiLoggerController; import gearth.ui.logger.loggerdisplays.PacketLogger;
import javafx.event.Event; import javafx.event.Event;
import javafx.fxml.FXMLLoader; import javafx.fxml.FXMLLoader;
import javafx.scene.Parent; import javafx.scene.Parent;

View File

@ -1,5 +1,8 @@
package gearth.ui; package gearth.ui.logger.loggerdisplays.uilogger;
import gearth.misc.harble_api.HarbleAPI;
import gearth.misc.harble_api.HarbleAPIFetcher;
import gearth.protocol.HMessage;
import gearth.protocol.HPacket; import gearth.protocol.HPacket;
import gearth.ui.logger.loggerdisplays.PacketLogger; import gearth.ui.logger.loggerdisplays.PacketLogger;
import javafx.application.Platform; import javafx.application.Platform;
@ -27,6 +30,9 @@ public class UiLoggerController implements Initializable {
public Label lblAutoScrolll; public Label lblAutoScrolll;
public CheckMenuItem chkAutoscroll; public CheckMenuItem chkAutoscroll;
public CheckMenuItem chkSkipBigPackets; public CheckMenuItem chkSkipBigPackets;
public CheckMenuItem chkMessageName;
public CheckMenuItem chkMessageHash;
public Label lblHarbleAPI;
private StyleClassedTextArea area; private StyleClassedTextArea area;
@ -35,7 +41,8 @@ public class UiLoggerController implements Initializable {
private boolean displayStructure = true; private boolean displayStructure = true;
private boolean autoScroll = true; private boolean autoScroll = true;
private boolean skiphugepackets = true; private boolean skiphugepackets = true;
private boolean viewMessageName = true;
private boolean viewMessageHash = false;
private volatile boolean initialized = false; private volatile boolean initialized = false;
private final List<Element> appendLater = new ArrayList<>(); private final List<Element> appendLater = new ArrayList<>();
@ -86,6 +93,25 @@ public class UiLoggerController implements Initializable {
String expr = packet.toExpression(); String expr = packet.toExpression();
lblHarbleAPI.setText("HarbleAPI: " + (HarbleAPIFetcher.HARBLEAPI == null ? "False" : "True"));
if ((viewMessageName || viewMessageHash) && HarbleAPIFetcher.HARBLEAPI != null) {
HarbleAPI api = HarbleAPIFetcher.HARBLEAPI;
HarbleAPI.HarbleMessage message = api.getHarbleMessageFromHeaderId(
(isIncoming ? HMessage.Side.TOCLIENT : HMessage.Side.TOSERVER),
packet.headerId()
);
if (!(viewMessageName && !viewMessageHash && message.getName() == null)) {
if (viewMessageName && message.getName() != null) {
elements.add(new Element("["+message.getName()+"]", "messageinfo"));
}
if (viewMessageHash) {
elements.add(new Element("["+message.getHash()+"]", "messageinfo"));
}
elements.add(new Element("\n", ""));
}
}
if (isBlocked) elements.add(new Element("[Blocked]\n", "blocked")); if (isBlocked) elements.add(new Element("[Blocked]\n", "blocked"));
else if (isReplaced) elements.add(new Element("[Replaced]\n", "replaced")); else if (isReplaced) elements.add(new Element("[Replaced]\n", "replaced"));
@ -180,14 +206,12 @@ public class UiLoggerController implements Initializable {
public void toggleSkipPackets(ActionEvent actionEvent) { public void toggleSkipPackets(ActionEvent actionEvent) {
skiphugepackets = !skiphugepackets; skiphugepackets = !skiphugepackets;
} }
}
class Element { public void toggleMessageName(ActionEvent actionEvent) {
final String text; viewMessageName = !viewMessageName;
final String className; }
Element(String text, String className) { public void toggleMessageHash(ActionEvent actionEvent) {
this.text = text; viewMessageHash = !viewMessageHash;
this.className = className;
} }
} }

View File

@ -9,13 +9,15 @@
<?import javafx.scene.layout.BorderPane?> <?import javafx.scene.layout.BorderPane?>
<?import javafx.scene.layout.FlowPane?> <?import javafx.scene.layout.FlowPane?>
<BorderPane fx:id="borderPane" prefHeight="560.0" prefWidth="820.0" xmlns="http://javafx.com/javafx/8.0.112" xmlns:fx="http://javafx.com/fxml/1" fx:controller="gearth.ui.UiLoggerController"> <BorderPane fx:id="borderPane" prefHeight="560.0" prefWidth="820.0" xmlns="http://javafx.com/javafx/10.0.1" xmlns:fx="http://javafx.com/fxml/1" fx:controller="gearth.ui.logger.loggerdisplays.uilogger.UiLoggerController">
<top> <top>
<MenuBar BorderPane.alignment="CENTER"> <MenuBar BorderPane.alignment="CENTER">
<Menu mnemonicParsing="false" text="View"> <Menu mnemonicParsing="false" text="View">
<Menu mnemonicParsing="false" text="Display Details"> <Menu mnemonicParsing="false" text="Display Details">
<items> <items>
<CheckMenuItem fx:id="chkDisplayStructure" mnemonicParsing="false" onAction="#toggleDisplayStructure" selected="true" text="Structure" /> <CheckMenuItem fx:id="chkDisplayStructure" mnemonicParsing="false" onAction="#toggleDisplayStructure" selected="true" text="Structure" />
<CheckMenuItem fx:id="chkMessageName" mnemonicParsing="false" onAction="#toggleMessageName" selected="true" text="Message Name" />
<CheckMenuItem fx:id="chkMessageHash" mnemonicParsing="false" onAction="#toggleMessageHash" text="Message Hash" />
</items> </items>
</Menu> </Menu>
<CheckMenuItem fx:id="chkViewIncoming" mnemonicParsing="false" onAction="#toggleViewIncoming" selected="true" text="View Incoming"> <CheckMenuItem fx:id="chkViewIncoming" mnemonicParsing="false" onAction="#toggleViewIncoming" selected="true" text="View Incoming">
@ -59,7 +61,20 @@
<Insets right="10.0" /> <Insets right="10.0" />
</FlowPane.margin> </FlowPane.margin>
</Label> </Label>
<Label fx:id="lblAutoScrolll" layoutX="151.0" layoutY="11.0" style="-fx-text-fill: black !important" text="Autoscroll: True" /> <Label fx:id="lblAutoScrolll" layoutX="151.0" layoutY="11.0" style="-fx-text-fill: black !important" text="Autoscroll: True">
<FlowPane.margin>
<Insets right="10.0" />
</FlowPane.margin></Label>
<Label layoutX="270.0" layoutY="11.0" text="|">
<FlowPane.margin>
<Insets right="10.0" />
</FlowPane.margin>
</Label>
<Label fx:id="lblHarbleAPI" layoutX="283.0" layoutY="11.0" style="-fx-text-fill: black !important" text="HarbleAPI: False">
<FlowPane.margin>
<Insets right="10.0" />
</FlowPane.margin>
</Label>
</FlowPane> </FlowPane>
</bottom> </bottom>
</BorderPane> </BorderPane>

View File

@ -3,6 +3,10 @@
-fx-fill: #a9a9a9; -fx-fill: #a9a9a9;
} }
.messageinfo {
-fx-fill: #D0D3D4;
}
.blocked, .replaced { .blocked, .replaced {
-fx-fill: #ffff00; -fx-fill: #ffff00;
} }