|
|
|
|
|
Description |
This library aims to make writing XMPP clients (in particular
bots) easy and fun. Here is a small example:
import XMPP
import Network
-- The bot's JID is "bot@example.com"
botUsername = "bot"
botServer = "example.com"
botPassword = "secret"
main :: IO ()
main = withSocketsDo $
do
-- Connect to server...
c <- openStream botServer
getStreamStart c
runXMPP c $ do
-- ...authenticate...
startAuth botUsername botServer botPassword
sendPresence
-- ...and do something.
run
run :: XMPP ()
run = do
-- Wait for an incoming message...
msg <- waitForStanza (isChat `conj` hasBody)
let sender = maybe "" id (getAttr "from" msg)
len = length $ maybe "" id (getMessageBody msg)
-- ...answer...
sendMessage sender ("Your message was "++(show len)++" characters long.")
-- ...and repeat.
run
XMPP is a protocol for streaming XML also known as Jabber. It is
described in RFCs 3920 and 3921, and in a series of XMPP Extension
Protocols (XEPs). All of this can be found at
http://www.xmpp.org.
For a larger example, see werewolf.
|
|
Synopsis |
|
|
|
|
The XMPP monad
|
|
data XMPP a |
A function in the XMPP monad behaves a bit like a thread in a
cooperative threading system: when it decides to wait for more
input, it "sleeps", letting other "threads" run, until input
matching a certain predicate arrives.
| Instances | |
|
|
runXMPP :: XMPPConnection c => c -> XMPP () -> IO () |
Run a function in the XMPP monad using the given XMPP connection.
After that, keep looping as long as there are handlers waiting for
incoming stanzas.
|
|
sendStanza :: XMLElem -> XMPP () |
Send an XMPP stanza.
|
|
addHandler |
:: StanzaPredicate | Stanza predicate.
| -> StanzaHandler | Stanza handler.
| -> Bool | Catch more than one stanza?
| -> XMPP () | | When a stanza matching the predicate arrives, call the given
handler. This is analogous to spawning a new thread, except that
the "thread" is only run if and when a matching stanza arrives.
Stanza handlers can be one-shot or permanent, as indicated by the
third argument.
|
|
|
waitForStanza :: StanzaPredicate -> XMPP XMLElem |
Suspend execution of current function while waiting for a stanza
matching the predicate.
|
|
quit :: XMPP () |
Terminate the loop as soon as the current function exits. This
works by removing all stanza handlers, which makes runXMPP exit.
|
|
type StanzaPredicate = XMLElem -> Bool |
A stanza predicate.
|
|
type StanzaHandler = XMLElem -> XMPP () |
A handler function for a stanza.
|
|
liftIO |
|
XML functions
|
|
data XMLElem |
A data structure representing an XML element.
| Constructors | XML String [(String, String)] [XMLElem] | Tags have a name, a list of attributes, and a list of
child elements.
| CData String | Character data just contains a string.
|
| Instances | |
|
|
xmlPath :: [String] -> XMLElem -> Maybe XMLElem |
Follow a "path" of named subtags in an XML tree. For every
element in the given list, find the subtag with that name and
proceed recursively.
|
|
getAttr :: String -> XMLElem -> Maybe String |
Get the value of an attribute in the given tag.
|
|
getCdata :: XMLElem -> Maybe String |
Get the character data subelement of the given tag.
|
|
xmlToString :: Bool -> XMLElem -> String |
Convert the tag back to XML. If the first parameter is true,
close the tag.
|
|
Stanza manipulation
|
|
sendIq |
:: String | JID of recipient
| -> String | Type of IQ, either "get" or "set"
| -> [XMLElem] | Payload elements
| -> XMPP String | ID of sent stanza
| Send an IQ request, returning the randomly generated ID.
|
|
|
sendIqWait |
:: String | JID of recipient
| -> String | Type of IQ, either "get" or "set"
| -> [XMLElem] | Payload elements
| -> XMPP XMLElem | Response stanza
| Send an IQ request and wait for the response, without blocking
other activity.
|
|
|
hasBody :: StanzaPredicate |
Return true if the message stanza has body text.
|
|
getMessageBody :: XMLElem -> Maybe String |
Get the body text of the message stanza, if any.
|
|
sendMessage |
:: String | JID of recipient
| -> String | Text of message
| -> XMPP () | | Send an ordinary "chat" type message.
|
|
|
sendPresence :: XMPP () |
Send ordinary online presence.
|
|
conj :: (a -> Bool) -> (a -> Bool) -> a -> Bool |
Conjunction ("and") of two predicates.
|
|
attributeMatches |
:: String | Attribute name
| -> (String -> Bool) | Attribute value predicate
| -> StanzaPredicate | | Apply the predicate to the named attribute. Return false if the
tag has no such attribute.
|
|
|
isMessage :: StanzaPredicate |
Return true if the tag is a message stanza.
|
|
isPresence :: StanzaPredicate |
Return true if the tag is a presence stanza.
|
|
isIq :: StanzaPredicate |
Return true if the tag is an IQ stanza.
|
|
isChat :: StanzaPredicate |
Return true if the tag is a chat message.
|
|
isFrom :: String -> StanzaPredicate |
Return true if the stanza is from the given JID.
|
|
iqXmlns :: String -> StanzaPredicate |
Return true if the stanza is an IQ stanza in the given namespace.
|
|
iqGet :: String -> StanzaPredicate |
Return true if the stanza is a "get" request in the given namespace.
|
|
iqSet :: String -> StanzaPredicate |
Return true if the stanza is a "set" request in the given namespace.
|
|
handleVersion |
:: String | Client name
| -> String | Client version
| -> String | Operating system
| -> XMPP () | | Establish a handler for answering to version requests with the
given information. See XEP-0092: Software Version.
|
|
|
JID functions
|
|
getUsername :: String -> String |
Get username part of JID, i.e. the part before the @ sign.
Return "" if the JID contains no @ sign.
|
|
getResource :: String -> String |
Get resource part of JID, i.e. the part after /.
Return "" if the JID has no resource.
|
|
getBareJid :: String -> String |
Get the bare JID, i.e. everything except the resource.
|
|
Authentication
|
|
startAuth |
:: String | Username (part before @ in JID)
| -> String | Server (part after @ in JID)
| -> String | Resource (unique identifier for this connection)
| -> XMPP () | | Perform authentication, following XEP-0078. Note that the
password will be sent in cleartext; this is not by design. Calls
error if authentication fails.
|
|
|
TCP connections
|
|
data TCPConnection |
An XMPP connection over TCP.
| Instances | |
|
|
openStream :: String -> IO TCPConnection |
Open a TCP connection to the named server, port 5222, and send a
stream header. This should really check SRV records.
|
|
getStreamStart :: TCPConnection -> IO XMLElem |
Get the stream header that the server sent. This needs to be
called before doing anything else with the stream.
|
|
Abstract connections
|
|
class XMPPConnection c where |
A class for various kinds of XMPP connections.
| | Methods | getStanzas :: c -> IO [XMLElem] | Get incoming stanzas from the connection.
| | sendStanza :: c -> XMLElem -> IO () | Send a stanza on the connection.
| | closeConnection :: c -> IO () | Close the connection.
|
| | Instances | |
|
|
Produced by Haddock version 0.7 |