clix.lua

Tue, 12 Jan 2010 02:17:58 +0000

author
Matthew Wild <mwild1@gmail.com>
date
Tue, 12 Jan 2010 02:17:58 +0000
changeset 28
c2998f70dfd4
parent 23
c5f04bdc7c64
child 32
cda6a004ff79
permissions
-rwxr-xr-x

clix: Pass short_help option to modules correctly

4
ead275885948 clix.lua: Add shebang for people who don't use squish
Matthew Wild <mwild1@gmail.com>
parents: 2
diff changeset
1 #!/usr/bin/env lua
5
7209e1f8e66b clix.lua, COPYING: Add COPYING file with MIT license, add copyright header to clix.lua
Matthew Wild <mwild1@gmail.com>
parents: 4
diff changeset
2 -- Clix -- Command-line XMPP
7209e1f8e66b clix.lua, COPYING: Add COPYING file with MIT license, add copyright header to clix.lua
Matthew Wild <mwild1@gmail.com>
parents: 4
diff changeset
3 -- Copyright (C) 2008-2010 Matthew Wild
7209e1f8e66b clix.lua, COPYING: Add COPYING file with MIT license, add copyright header to clix.lua
Matthew Wild <mwild1@gmail.com>
parents: 4
diff changeset
4 --
7209e1f8e66b clix.lua, COPYING: Add COPYING file with MIT license, add copyright header to clix.lua
Matthew Wild <mwild1@gmail.com>
parents: 4
diff changeset
5 -- This project is MIT/X11 licensed. Please see the
7209e1f8e66b clix.lua, COPYING: Add COPYING file with MIT license, add copyright header to clix.lua
Matthew Wild <mwild1@gmail.com>
parents: 4
diff changeset
6 -- COPYING file in the source package for more information.
7209e1f8e66b clix.lua, COPYING: Add COPYING file with MIT license, add copyright header to clix.lua
Matthew Wild <mwild1@gmail.com>
parents: 4
diff changeset
7 --
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
8 require "verse"
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
9 require "verse.client"
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
10
8
df4cb4a73549 clix: Make short_opts table global, to allow commands to add their own short options
Matthew Wild <mwild1@gmail.com>
parents: 7
diff changeset
11 -- Global to allow commands to add to it
23
c5f04bdc7c64 clix, clix.raw: Move 'Connected as' to clix_connect(), and suppress on -q/--quiet
Matthew Wild <mwild1@gmail.com>
parents: 21
diff changeset
12 short_opts = { v = "verbose", q = "quiet", t = "to", f = "from", e = "type",
c5f04bdc7c64 clix, clix.raw: Move 'Connected as' to clix_connect(), and suppress on -q/--quiet
Matthew Wild <mwild1@gmail.com>
parents: 21
diff changeset
13 a = "account", p = "password", r = "resource", o = "presence", c = "chatroom" }
8
df4cb4a73549 clix: Make short_opts table global, to allow commands to add their own short options
Matthew Wild <mwild1@gmail.com>
parents: 7
diff changeset
14
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
15 local command = arg[1];
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
16
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
17 if not command then
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
18 print("Command Line XMPP, available commands:");
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
19 for module in pairs(package.preload) do
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
20 if module:match("^clix%.") then
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
21 local m = require(module);
28
c2998f70dfd4 clix: Pass short_help option to modules correctly
Matthew Wild <mwild1@gmail.com>
parents: 23
diff changeset
22 io.write("\t", module:gsub("^clix%.", ""), ": ");
c2998f70dfd4 clix: Pass short_help option to modules correctly
Matthew Wild <mwild1@gmail.com>
parents: 23
diff changeset
23 m({ short_help = true }, {});
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
24 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
25 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
26 return 0;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
27 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
28
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
29 local ok, m = pcall(require, "clix."..command);
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
30 if not ok then
20
80cc61512f10 clix: Allow --debug to be anywhere on the command-line
Matthew Wild <mwild1@gmail.com>
parents: 17
diff changeset
31 local is_debug;
80cc61512f10 clix: Allow --debug to be anywhere on the command-line
Matthew Wild <mwild1@gmail.com>
parents: 17
diff changeset
32 for i=1,#arg do
80cc61512f10 clix: Allow --debug to be anywhere on the command-line
Matthew Wild <mwild1@gmail.com>
parents: 17
diff changeset
33 if arg[i] == "--debug" then
80cc61512f10 clix: Allow --debug to be anywhere on the command-line
Matthew Wild <mwild1@gmail.com>
parents: 17
diff changeset
34 is_debug = true; break;
80cc61512f10 clix: Allow --debug to be anywhere on the command-line
Matthew Wild <mwild1@gmail.com>
parents: 17
diff changeset
35 end
80cc61512f10 clix: Allow --debug to be anywhere on the command-line
Matthew Wild <mwild1@gmail.com>
parents: 17
diff changeset
36 end
80cc61512f10 clix: Allow --debug to be anywhere on the command-line
Matthew Wild <mwild1@gmail.com>
parents: 17
diff changeset
37 print("Error running command '"..command..(is_debug and "" or "' (run with --debug to see full error)"));
80cc61512f10 clix: Allow --debug to be anywhere on the command-line
Matthew Wild <mwild1@gmail.com>
parents: 17
diff changeset
38 if is_debug then
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
39 print(m);
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
40 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
41 return 1;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
42 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
43
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
44 if type(m) ~= "function" then
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
45 print(command.." is not a valid command");
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
46 return 1;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
47 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
48
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
49 local accounts = { default = {} };
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
50 local current_account;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
51 for line in io.lines(os.getenv("HOME").."/.clix") do
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
52 line = line:match("^%s*(.-)%s*$");
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
53 if line:match("^%[") then
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
54 current_account = line:match("^%[(.-)%]");
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
55 accounts[current_account] = {};
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
56 if not current_account then -- This is the first defined account
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
57 accounts.default = accounts[current_account];
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
58 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
59 elseif current_account then
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
60 local k,v = line:match("^(%w+)%s*[:=]%s*(.+)$");
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
61 accounts[current_account or "default"][k] = v;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
62 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
63 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
64
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
65 function clix_connect(opts, on_connect)
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
66 local account = accounts[opts.account or "default"];
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
67 if not (account and account.jid) then
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
68 io.stderr:write("The specified account (", opts.account or "default", ") wasn't found in the config file\n");
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
69 return nil;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
70 end
7
6078e8d2b59d clix: Enable global Verse logger when verbose is enabled
Matthew Wild <mwild1@gmail.com>
parents: 5
diff changeset
71 verse.set_logger(opts.verbose and print or function () end);
2
fd77e75c4891 clix: Make more use of Verse's new logging controls
Matthew Wild <mwild1@gmail.com>
parents: 0
diff changeset
72 local conn = verse.new(verse.logger());
fd77e75c4891 clix: Make more use of Verse's new logging controls
Matthew Wild <mwild1@gmail.com>
parents: 0
diff changeset
73 conn.log.debug = opts.verbose;
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
74 conn:hook("authentication-failure", function (err)
2
fd77e75c4891 clix: Make more use of Verse's new logging controls
Matthew Wild <mwild1@gmail.com>
parents: 0
diff changeset
75 conn:error("Authentication failure ("..(err.condition or "unknown error")..")"..(err.text and (": "..err.text) or ""));
14
1e927484c6ec clix: Close connection after fatal error during login
Matthew Wild <mwild1@gmail.com>
parents: 13
diff changeset
76 conn:close();
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
77 end);
17
fa9efbef8a0c Move presence sending into clix_connect(), and control with -o/--presence
Matthew Wild <mwild1@gmail.com>
parents: 15
diff changeset
78 conn:hook("binding-success", function ()
23
c5f04bdc7c64 clix, clix.raw: Move 'Connected as' to clix_connect(), and suppress on -q/--quiet
Matthew Wild <mwild1@gmail.com>
parents: 21
diff changeset
79 if not opts.quiet then
c5f04bdc7c64 clix, clix.raw: Move 'Connected as' to clix_connect(), and suppress on -q/--quiet
Matthew Wild <mwild1@gmail.com>
parents: 21
diff changeset
80 io.stderr:write("clix: connected as ", conn.jid, "\n");
c5f04bdc7c64 clix, clix.raw: Move 'Connected as' to clix_connect(), and suppress on -q/--quiet
Matthew Wild <mwild1@gmail.com>
parents: 21
diff changeset
81 end
21
cdeb02d9546d clix, clix.send: Support for chatrooms (-c/--chatroom with --nick=somenick)
Matthew Wild <mwild1@gmail.com>
parents: 20
diff changeset
82 if opts.chatroom then
cdeb02d9546d clix, clix.send: Support for chatrooms (-c/--chatroom with --nick=somenick)
Matthew Wild <mwild1@gmail.com>
parents: 20
diff changeset
83 conn:send(verse.presence{to=opts.to.."/"..(opts.nick or "clix")});
cdeb02d9546d clix, clix.send: Support for chatrooms (-c/--chatroom with --nick=somenick)
Matthew Wild <mwild1@gmail.com>
parents: 20
diff changeset
84 end
17
fa9efbef8a0c Move presence sending into clix_connect(), and control with -o/--presence
Matthew Wild <mwild1@gmail.com>
parents: 15
diff changeset
85 if opts.presence then
fa9efbef8a0c Move presence sending into clix_connect(), and control with -o/--presence
Matthew Wild <mwild1@gmail.com>
parents: 15
diff changeset
86 conn:send(verse.presence());
fa9efbef8a0c Move presence sending into clix_connect(), and control with -o/--presence
Matthew Wild <mwild1@gmail.com>
parents: 15
diff changeset
87 end
fa9efbef8a0c Move presence sending into clix_connect(), and control with -o/--presence
Matthew Wild <mwild1@gmail.com>
parents: 15
diff changeset
88 return on_connect(conn);
fa9efbef8a0c Move presence sending into clix_connect(), and control with -o/--presence
Matthew Wild <mwild1@gmail.com>
parents: 15
diff changeset
89 end);
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
90 conn:hook("binding-failure", function (err)
2
fd77e75c4891 clix: Make more use of Verse's new logging controls
Matthew Wild <mwild1@gmail.com>
parents: 0
diff changeset
91 conn:error("Resource binding failure ("..(err.condition or "unknown error")..")"..(err.text and (": "..err.text) or ""));
14
1e927484c6ec clix: Close connection after fatal error during login
Matthew Wild <mwild1@gmail.com>
parents: 13
diff changeset
92 conn:close();
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
93 end);
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
94 conn:hook("disconnected", function (info)
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
95 if info.reason then
2
fd77e75c4891 clix: Make more use of Verse's new logging controls
Matthew Wild <mwild1@gmail.com>
parents: 0
diff changeset
96 conn:warn("Disconnecting: %s", tostring(info.reason));
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
97 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
98 verse.quit();
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
99 end);
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
100 -- Optional config parameters
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
101 conn.connect_host = account.address;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
102 conn.connect_port = account.port;
13
751db005032e clix: Allow specifying the resource with -r/--resource
Matthew Wild <mwild1@gmail.com>
parents: 11
diff changeset
103
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
104 -- Connect!
15
54314164a2a3 clix: Allow -p/--password to specify the login password
Matthew Wild <mwild1@gmail.com>
parents: 14
diff changeset
105 conn:connect_client(account.jid, opts.password or account.password);
11
a502c905527c clix: Handle errors (including 'interrupted!') in verse.loop()
Matthew Wild <mwild1@gmail.com>
parents: 8
diff changeset
106
13
751db005032e clix: Allow specifying the resource with -r/--resource
Matthew Wild <mwild1@gmail.com>
parents: 11
diff changeset
107 if type(opts.resource) == "string" then
751db005032e clix: Allow specifying the resource with -r/--resource
Matthew Wild <mwild1@gmail.com>
parents: 11
diff changeset
108 conn.resource = opts.resource;
751db005032e clix: Allow specifying the resource with -r/--resource
Matthew Wild <mwild1@gmail.com>
parents: 11
diff changeset
109 end
751db005032e clix: Allow specifying the resource with -r/--resource
Matthew Wild <mwild1@gmail.com>
parents: 11
diff changeset
110
11
a502c905527c clix: Handle errors (including 'interrupted!') in verse.loop()
Matthew Wild <mwild1@gmail.com>
parents: 8
diff changeset
111 local ok, ret = pcall(verse.loop);
a502c905527c clix: Handle errors (including 'interrupted!') in verse.loop()
Matthew Wild <mwild1@gmail.com>
parents: 8
diff changeset
112 if not ok and not ret:match("interrupted!$") then
a502c905527c clix: Handle errors (including 'interrupted!') in verse.loop()
Matthew Wild <mwild1@gmail.com>
parents: 8
diff changeset
113 io.stderr:write("Fatal error: ", ret, "\n");
a502c905527c clix: Handle errors (including 'interrupted!') in verse.loop()
Matthew Wild <mwild1@gmail.com>
parents: 8
diff changeset
114 return 1;
a502c905527c clix: Handle errors (including 'interrupted!') in verse.loop()
Matthew Wild <mwild1@gmail.com>
parents: 8
diff changeset
115 end
a502c905527c clix: Handle errors (including 'interrupted!') in verse.loop()
Matthew Wild <mwild1@gmail.com>
parents: 8
diff changeset
116 return err or 0;
0
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
117 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
118
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
119 table.remove(arg,1);
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
120
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
121 local opts = {};
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
122
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
123 local args_handled_up_to;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
124 for i, opt in ipairs(arg) do
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
125 if opt:match("^%-") and opt ~= "--" then
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
126 local name = opt:match("^%-%-?([^%s=]+)()")
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
127 name = (short_opts[name] or name):gsub("%-+", "_");
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
128 if name:match("^no_") then
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
129 name = name:sub(4, -1);
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
130 opts[name] = false;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
131 else
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
132 opts[name] = opt:match("=(.*)$") or true;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
133 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
134 else
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
135 args_handled_up_to = i-1;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
136 break;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
137 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
138 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
139
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
140 -- Remove all the handled args from the arg array
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
141 for n=(args_handled_up_to or #arg),1,-1 do
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
142 table.remove(arg, n);
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
143 end
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
144
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
145 return m(opts, arg) or 0;
ae83411a89c9 Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff changeset
146

mercurial