sclass GazelleTalkToBot { long botID; // Gazelle post ID S cookie = "test_" + aGlobalID(); int n; // number of messages loaded double timeout = 70; new L msgs; *(long *botID) {} swappable void onNewDialog() {} swappable void onNewMsg(Msg msg) {} // may block for 60 seconds. returns HTML public S get() { // TODO: I think cruddie.site doesn't close existing connections when rebooting (?) S json = loadPageWithTimeoutAndParamsSilently(timeout, "https://gazelle.rocks/incremental", +cookie, _botConfig := "codePost=" + botID, json := 1, a := zeroToNull(n)); Map map = decodeJSONMap(json); onResult(map); } swappable void onResult(Map map) { if (map.containsKey("n")) n = map.get("n"); if (isTrue(map.get("newDialog"))) onNewDialog(); fOr (Map m : (L) map.get("msgs")) { new Msg msg; msg.fromUser = isTrue(m.get("fromUser")); msg.text = (S) m.get("text"); msg.time = toLong(m.get("time")); msgs.add(msg); pcall { onNewMsg(msg); } } } }