2 * Copyright (c) 2010, 2011, Jonathan Schleifer <js@webkeks.org>
3 * Copyright (c) 2011, Florian Zeitz <florob@babelmonkeys.de>
5 * http://cgit.babelmonkeys.de/cgit.cgi/mpdbot/
7 * Permission to use, copy, modify, and/or distribute this software for any
8 * purpose with or without fee is hereby granted, provided that the above
9 * copyright notice and this permission notice is present in all copies.
11 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
12 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
13 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
14 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
15 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
16 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
17 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
18 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
19 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
20 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
21 * POSSIBILITY OF SUCH DAMAGE.
24 #import <ObjFW/ObjFW.h>
25 #import <ObjXMPP/ObjXMPP.h>
29 #define NS_DISCO_INFO @"http://jabber.org/protocol/disco#info"
31 @interface AppDelegate: OFObject <OFApplicationDelegate, XMPPConnectionDelegate>
34 MPDConnection *mpdConn;
38 OF_APPLICATION_DELEGATE(AppDelegate)
40 @implementation AppDelegate
41 - (void)applicationDidFinishLaunching
47 OFString *mpd_port_string;
49 OFDictionary *environment = [OFApplication environment];
50 OFArray *arguments = [OFApplication arguments];
52 conn = [[XMPPConnection alloc] init];
53 [conn addDelegate: self];
55 if (arguments.count != 3) {
56 [of_stdout writeFormat: @"Usage: %@ <server> <user> <passwd>\n",
57 [OFApplication programName]];
58 [OFApplication terminateWithStatus: 1];
61 conn.domain = [arguments objectAtIndex: 0];
62 conn.username = [arguments objectAtIndex: 1];
63 conn.password = [arguments objectAtIndex: 2];
64 conn.resource = @"ObjXMPP";
66 mpd_host = [environment objectForKey: @"MPD_HOST"];
68 mpd_host = @"localhost";
70 mpd_port_string = [environment objectForKey: @"MPD_PORT"];
71 if (mpd_port_string && [mpd_port_string decimalValue] <= UINT16_MAX)
72 mpd_port = (uint16_t) [mpd_port_string decimalValue];
76 mpdConn = [[MPDConnection alloc] initWithHost: mpd_host
82 [conn handleConnection];
84 [of_stderr writeFormat: @"%@\n", e];
88 - (void)connectionWasAuthenticated: (XMPPConnection*)conn
90 [of_stdout writeLine: @"Auth successful"];
93 - (void)connection: (XMPPConnection*)conn
94 wasBoundToJID: (XMPPJID*)jid
100 [of_stdout writeFormat: @"Bound to JID: %@\n", [jid fullJID]];
102 pres = [XMPPPresence presence];
103 [pres addPriority: 0];
104 [pres addStatus: @"Hello I'm MPDbot!"];
105 [conn sendStanza: pres];
107 discoID = [[conn generateStanzaID] retain];
108 disco = [XMPPIQ IQWithType: @"get"
110 disco.to = [XMPPJID JIDWithString: [[conn JID] bareJID]];
111 [disco addChild: [OFXMLElement
112 elementWithName: @"query"
113 namespace: NS_DISCO_INFO]];
116 withCallbackObject: self
117 selector: @selector(mpdbot_handleDiscoForConnection:withIQ:)];
120 - (BOOL)mpdbot_handleDiscoForConnection: (XMPPConnection*)conn
123 OFXMLElement *query = [iq elementForName: @"query"
124 namespace: NS_DISCO_INFO];
125 for (OFXMLElement *identity in [query elementsForName: @"identity"
126 namespace: NS_DISCO_INFO]) {
127 if ([[[identity attributeForName: @"category"]
128 stringValue] isEqual: @"pubsub"] &&
129 [[[identity attributeForName: @"type"] stringValue]
131 pepper = [[PEPThread alloc] initWithObject: conn];
137 [of_stderr writeLine: @"Server does NOT support PEP"];
142 - (void)connection: (XMPPConnection*)conn
143 didReceivePresence: (XMPPPresence*)pres
145 if ([pres.type isEqual: @"subscribe"]) {
146 XMPPPresence *answer;
147 answer = [XMPPPresence presenceWithType: @"subscribed"
149 answer.to = [XMPPJID JIDWithString: [pres.from bareJID]];
150 [conn sendStanza: answer];
154 - (void)connection: (XMPPConnection*)conn
155 didReceiveMessage: (XMPPMessage*)mesg
157 if ([mesg.body isEqual: @"pause"]) {
158 [mpdConn send: @"pause"];
163 - (void)connectionWasClosed: (XMPPConnection*)conn
165 [of_stdout writeLine: @"Connection was closed!"];