# HG changeset patch # User Stiletto # Date 1351002829 -14400 # Node ID 4e050075fab9a7cf74beb8f130d95c5d6ea43a32 # Parent 76caf6a3f413a42611546a17a781a24f9556de33 Level of stubbornness skyrocketed diff -r 76caf6a3f413 -r 4e050075fab9 iswydt.vala --- a/iswydt.vala Fri Oct 19 00:38:54 2012 +0400 +++ b/iswydt.vala Tue Oct 23 18:33:49 2012 +0400 @@ -24,6 +24,7 @@ public Module[] modules; public signal void state_changed(State old_state, State new_state, string description); + public signal void check_time(); protected void _change_state(State new_state, string description) { var old_state = this._state; if (old_state != new_state) { @@ -90,6 +91,10 @@ this.rooms[room.jid] = room;*/ } }); + check_time.connect( () => { + if (_state == State.DISCONNECTED) + open(); + }); } public void open() { @@ -137,8 +142,15 @@ var cfg = new Config.from_file(args[1]); var loop = new MainLoop(); var account = new Connection(cfg); - account.open(); + //account.open(); stdout.printf("Fuck yeah\n"); + var checktimer = new TimeoutSource(2000); + checktimer.set_callback(() => { + account.check_time(); + //stderr.printf("TimeoutSource OLOLO\n"); + return true; + }); + checktimer.attach(loop.get_context()); loop.run(); return 0; } diff -r 76caf6a3f413 -r 4e050075fab9 muc.vala --- a/muc.vala Fri Oct 19 00:38:54 2012 +0400 +++ b/muc.vala Tue Oct 23 18:33:49 2012 +0400 @@ -10,6 +10,8 @@ } class ModuleMuc : Module { + public static const string NS_MUC_USER = "http://jabber.org/protocol/muc#user"; + public enum Affiliation { NONE, OUTCAST, @@ -66,12 +68,14 @@ public signal void on_role(Conference conf, Occupant occupant, Role prev); public signal void on_affil(Conference conf, Occupant occupant, Affiliation prev); public signal void on_nick(Conference conf, Occupant occupant, string prev); + public signal void on_message(Conference conf, Occupant occupant, Lm.MessageNode message, string body); public signal void on_subject(Conference conf); public class Conference : Object { public string jid; public string nick; public string desired_nick; + public bool enabled; public string subject; protected State _state; @@ -87,6 +91,8 @@ this._state = new_state; stderr.printf("MUC State changed %s -> %s : %s\n",old_state.to_string(), new_state.to_string(), description); module.state_changed(this, old_state, new_state, description); + if (new_state == State.DISCONNECTED) + occupants.clear(); } else stderr.printf("MUC State not changed %s : %s\n",old_state.to_string(), description); } @@ -94,7 +100,7 @@ public Conference(ModuleMuc module, string jid) { this.module = module; var section = "muc "+jid; - this.desired_nick = module.cfg[section,"nick"]; + this.desired_nick = module.cfg.get_default(section,"nick",module.cfg.get_default("muc","nick",Random.next_int().to_string())); this.nick = this.desired_nick; this.jid = jid; this._state = State.DISCONNECTED; @@ -108,7 +114,7 @@ prs.node.add_child("x",null).set_attribute("xmlns","http://jabber.org/protocol/muc"); module.conn.cn.send(prs); nick = desired_nick; - _change_state(State.CONNECTING, "requested to join"); + _change_state(State.CONNECTING, "requested to join: "+desc); } } @@ -123,41 +129,51 @@ case "unavailable": if (from.length==2) { var statuses = new Gee.HashSet(); + var occupant = occupants[from[1]]; + var affil = Affiliation.NONE; + var role = Role.NONE; + string prs_nick = null; - var x = node.get_child("x"); - var child = x!=null ? x.children : null; - while (child != null) { - stdout.printf("Child %s %s\n", child.name, child.get_attribute("code")); - if (child.name == "status") { - var code = child.get_attribute("code"); - if (code!=null) - statuses.add(code.to_int()); + var chn = node.children; + while (chn != null) { + switch (chn.name) { + + case "x": + switch (chn.get_attribute("xmlns")) { + case NS_MUC_USER: + var child = chn.children; + while (child != null) { + stdout.printf("Child %s %s\n", child.name, child.get_attribute("code")); + if (child.name == "status") { + var code = child.get_attribute("code"); + if (code!=null) + statuses.add(code.to_int()); + } + child = child.next; + } + var item = chn.get_child("item"); + if (item == null) + log("Muc", LogLevelFlags.LEVEL_ERROR, "Your MUC server is shit. No role and affiliation info in presences: %s", node.to_string()); + affil = affil_from_string(item.get_attribute("affiliation")); + role = role_from_string(item.get_attribute("role")); + prs_nick = item.get_attribute("nick"); + break; + } + break; } - child = child.next; + chn = chn.next; } if (statuses.contains(110) && (_state == State.CONNECTED)) log("Muc", LogLevelFlags.LEVEL_INFO, "Joined a room which I was already in: %s", from[0]); - var occupant = occupants[from[1]]; - var item = x != null ? x.get_child("item") : null; - var affil = Affiliation.NONE; - var role = Role.NONE; - string nick = null; - if (item != null) { - affil = affil_from_string(item.get_attribute("affiliation")); - role = role_from_string(item.get_attribute("role")); - nick = item.get_attribute("nick"); - } else - log("Muc", LogLevelFlags.LEVEL_ERROR, "Your MUC server is shit. No role and affiliation info in presences: %s", node.to_string()); if (occupant != null) { if (role == Role.NONE) { occupants.unset(from[1]); log("Muc", LogLevelFlags.LEVEL_INFO, "MUC<%s> %s has parted.", this.jid, from[1]); module.on_part(this, occupant); - if (from[1]==this.nick) { + if (occupant.isme) { _change_state(State.DISCONNECTED, "we became unavailable"); - occupants.clear(); } } else { if (affil != occupant.affil) { @@ -170,10 +186,10 @@ occupant.role = role; module.on_role(this, occupant, prev); } - if (statuses.contains(303) && (nick!=null)) { - occupants[nick] = occupant; + if (statuses.contains(303) && (prs_nick!=null)) { + occupants[prs_nick] = occupant; occupants.unset(from[1]); - occupant.nick = nick; + occupant.nick = prs_nick; module.on_nick(this, occupant, from[1]); } } @@ -186,8 +202,10 @@ occupants[from[1]] = occupant; occupant.isme = statuses.contains(110); log("Muc", LogLevelFlags.LEVEL_INFO, "MUC<%s> %s has joined as %s/%s.", this.jid, from[1], affil.to_string(), role.to_string()); - if (statuses.contains(110)) + if (statuses.contains(110)) { + this.nick = from[1]; _change_state(State.CONNECTED, "got own presence. we are "+this.nick); + } module.on_join(this, occupant); } @@ -214,11 +232,27 @@ this.subject = subj; module.on_subject(this); } + } else { + var occupant = (from.length > 1) ? occupants[from[1]] : null; + var body = node.find_child("body"); + module.on_message(this, occupant, node, (body!=null) ? body.get_value() : null); } } return Lm.HandlerResult.ALLOW_MORE_HANDLERS; } public void part(string desc) { + if (_state != State.DISCONNECTED) { + var prs = new Lm.Message(jid+"/"+desired_nick, Lm.MessageType.PRESENCE); + presence_join_id = jid+"_"+Random.next_int().to_string(); + prs.node.set_attribute("type","unavailable"); + prs.node.add_child("x",null).set_attribute("xmlns","http://jabber.org/protocol/muc"); + module.conn.cn.send(prs); + nick = desired_nick; + } + } + + public void connection_lost() { + _change_state(State.DISCONNECTED, "connection lost"); } } @@ -241,15 +275,37 @@ } return Lm.HandlerResult.ALLOW_MORE_HANDLERS; }, null); + var names = cfg.get_default("muc","mucs","").split(" "); + foreach (var name in names) { + var room = new Conference(this, name); //, "Ζαλυπα"); + //room.join("Oh hai"); + room.enabled = true; + this.rooms[room.jid] = room; + } conn.cn.register_message_handler(muc_handler, Lm.MessageType.MESSAGE, Lm.HandlerPriority.NORMAL); conn.cn.register_message_handler(muc_handler, Lm.MessageType.PRESENCE, Lm.HandlerPriority.NORMAL); conn.cn.register_message_handler(muc_handler, Lm.MessageType.IQ, Lm.HandlerPriority.NORMAL); conn.state_changed.connect( (olds, news, desc) => { - if (news == Connection.State.CONNECTED) { - var room = new Conference(this, "говнохост@conference.blasux.ru"); //, "Ζαλυπα"); - room.join("Oh hai"); - this.rooms[room.jid] = room; + switch (news) { + case Connection.State.CONNECTED: + break; + case Connection.State.DISCONNECTED: + foreach(var room in rooms.values) + room.connection_lost(); + break; } }); + conn.check_time.connect( () => { + if (conn.state == Connection.State.CONNECTED) + foreach (var room in rooms.values) { + if (room.enabled) { + if (room.state == State.DISCONNECTED) + room.join("Reconnect"); + } else { + if (room.state == State.CONNECTED) + room.part("Disabled"); + } + } + }); } }