damnpacket-1.0.0: Parsing dAmn messages

Safe HaskellNone




This module provides a datatype and convenience functions for parsing, manipulating, and rendering deviantART Message Network messages.



data Message Source #

A top-level dAmn message.

General syntax for a message:

name arg


As reflected in the field types of Message, the arg and body are both optional.

Attribute values are considered to be textual data and generally consist of part reasons, privclass names, users' "taglines" and so on. The message body can either be treated as text or as a SubMessage (see MessageBody).

Note that dAmn is a primarily browser-based platform; it deals with only ISO-8859-1 output and input and inserts chat messages directly into the DOM. As a consequence, correctly displaying characters past the ASCII block requires the use of HTML entities.

All functions in this module transparently convert HTML entities embedded in ByteStrings to Text (and back; see toBodyText). Thus, when Text appears in fields of this record or of SubMessage, you can assume that the HTML entity decoding step has already been handled.

data SubMessage Source #

A second-level dAmn message. Note that this message can omit the name/argument pair.

data MessageBody Source #

The body of a message, which can be converted to various formats (bodyWithFormat) or parsed as a SubMessage (subMessage).

Working with message bodies

bodyBytes :: MessageBody -> ByteString Source #

View the original binary content of a MessageBody.

To interpret this as textual data, use bodyWithFormat.

bodyWithFormat :: Monoid s => Formatter s -> MessageBody -> s Source #

Convert a MessageBody to some stringlike representation using the given Formatter. (See damnFormat).

toBodyText :: Text -> MessageBody Source #

Like toBody, but convert codepoints outside the ASCII range to HTML entities.

Note that this is NOT equivalent to toBody . encodeUtf8.

Working with sub-messages

subMessage :: MessageBody -> forall m. MonadFail m => m SubMessage Source #

Try to parse a MessageBody as a SubMessage.

pattern SubM :: SubMessage -> Maybe MessageBody Source #

subMessage as a pattern.

case messageBody of
    Sub (SubMessage name args attrs body)) -> ...
    _ -> error "No parse"

Can be nested:

isJoinPacket :: Message -> Bool
isJoinPacket (Message "recv" room _
    (Sub (SubMessage (Just "join") (Just uname) _
        (Sub (SubMessage Nothing Nothing userAttrs _)))))
    = True
isJoinPacket _ = False



render :: Message -> ByteString Source #

Convert a Message back into a ByteString to send to dAmn. The null byte is appended. In addition, all characters outside the ASCII block are converted to HTML entities, thus

>>> render (Message "foo" (Just "bar") [("attr1", "☭")] Nothing)
"foo bar\nattr1=☭\n\NUL"