packages feed

dbus-th (empty) → 0.1.0.0

raw patch · 5 files changed

+231/−0 lines, 5 filesdep +basedep +containersdep +dbus-coresetup-changed

Dependencies added: base, containers, dbus-core, syb, template-haskell, text

Files

+ DBus/TH.hs view
@@ -0,0 +1,131 @@+{-# LANGUAGE TemplateHaskell, TypeOperators, DeriveDataTypeable #-}++module DBus.TH+  (module Data.Int,+   module Data.Word,+   Proxy,+   Client, BusName,+   ObjectPath, InterfaceName,+   MemberName, Variant,+   connectSession, connectSystem,+   proxy,+   Signature (..),+   Function (..),+   (=::), as,+   interface+  ) where++import Control.Monad+import Data.Int+import Data.Word+import Language.Haskell.TH+import qualified Data.Text as Text+import Data.Char+import Data.List+import Data.Generics+import DBus.Client.Simple hiding (Type, Signature)++-- | Function signature+data Signature = Return Name+               | Name :-> Signature+  deriving (Eq, Show, Data, Typeable)++infixr 6 :->++-- | Function with DBus name and Haskell name+data Function = Function {+    fnName      :: String    -- ^ Function name to use in Haskell+  , fnDBusName  :: String    -- ^ Function name to use in DBus+  , fnSignature :: Signature -- ^ Function signature+    }+  deriving (Eq, Show, Data, Typeable)++-- | Create a Function from it's name and Signature.+-- Sets fnDBusName == fnName.+(=::) :: String -> Signature -> Function+name =:: sig = Function name name sig++infixr 5 =::++-- | Set specific Haskell name for Function.+as :: Function -> String -> Function+fn `as` name = fn {fnName = name}++infixl 4 `as`++nArgs :: Signature -> Int+nArgs (Return _) = 0+nArgs (_ :-> s)  = 1 + nArgs s++firstLower :: String -> String+firstLower [] = []+firstLower (x:xs) = toLower x: xs++-- | Generate bindings for methods in specific DBus interface.+-- If second argument is (Just prefix), then prefix will be+-- added to the beginning of all DBus names and removed from all+-- Haskell names.+interface :: String       -- ^ Interface name+          -> Maybe String -- ^ Prefix+          -> [Function]   -- ^ List of functions+          -> Q [Dec]+interface ifaceName mbPrefix fns = concat `fmap` mapM iface fns+  where+    iface :: Function -> Q [Dec]+    iface (Function name dbusName sig) =+        let name'     = strip name+            dbusName' = addPrefix dbusName+        in sequence [generateSignature name' sig,+                     generateImplementation name' dbusName' sig]++    addPrefix :: String -> String+    addPrefix s =+      case mbPrefix of+        Nothing     -> s+        Just prefix -> prefix ++ s++    strip :: String -> String+    strip s =+      case mbPrefix of+        Nothing     -> s+        Just prefix -> if prefix `isPrefixOf` s+                         then drop (length prefix) s+                         else s++    generateSignature :: String -> Signature -> Q Dec+    generateSignature name sig = do+        dbt <- dbusType (transformType sig)+        return $ SigD (mkName $ firstLower name) dbt++    dbusType :: Type -> Q Type+    dbusType t = [t| Proxy -> $(return t) |]++    transformType :: Signature -> Type+    transformType (Return t) = AppT (ConT ''IO) (AppT (ConT ''Maybe) (ConT t))+    transformType (t :-> s)  = AppT (AppT ArrowT (ConT t)) (transformType s)++    generateImplementation :: String -> String -> Signature -> Q Dec+    generateImplementation name dbusName sig = do+        let bus  = mkName "bus"+        args <- replicateM (nArgs sig) (newName "x")+        body <- generateBody dbusName sig args+        return $ FunD (mkName $ firstLower name) [Clause (VarP bus: map VarP args) (NormalB body) []]++    generateBody :: String -> Signature -> [Name] -> Q Exp+    generateBody name sig names = do+        [| do+           res <- call $(varE $ mkName "bus")+                       (interfaceName_ $ Text.pack ifaceName)+                       (memberName_ $ Text.pack name)+                       $(variant names) +           return $ fromVariant (res !! 0)+          |]++    variant :: [Name] -> Q Exp+    variant names = do+      exs <- mapM variant1 names+      return $ ListE exs++    variant1 :: Name -> Q Exp+    variant1 name = [| toVariant $(varE name) |]+
+ LICENSE view
@@ -0,0 +1,30 @@+Copyright (c) 2012, IlyaPortnov++All rights reserved.++Redistribution and use in source and binary forms, with or without+modification, are permitted provided that the following conditions are met:++    * Redistributions of source code must retain the above copyright+      notice, this list of conditions and the following disclaimer.++    * Redistributions in binary form must reproduce the above+      copyright notice, this list of conditions and the following+      disclaimer in the documentation and/or other materials provided+      with the distribution.++    * Neither the name of IlyaPortnov nor the names of other+      contributors may be used to endorse or promote products derived+      from this software without specific prior written permission.++THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ Setup.hs view
@@ -0,0 +1,2 @@+import Distribution.Simple+main = defaultMain
+ Test.hs view
@@ -0,0 +1,38 @@+{-# LANGUAGE TemplateHaskell, TypeOperators, OverloadedStrings #-}++import Control.Monad+import qualified Data.Map as M+import DBus.TH+import System.Environment++type Ints = [Int32]++type Buddies = M.Map String Int32++interface "im.pidgin.purple.PurpleInterface" (Just "Purple")+    [ "Strreplace" =:: ''String :-> ''String :-> ''String :-> Return ''String `as` "replace"+    , "AccountsFind" =:: ''String :-> ''String :-> Return ''Int32+    , "AccountsGetAllActive" =:: Return ''Ints+    , "FindBuddy" =:: ''Int32 :-> ''String :-> Return ''Int32+    , "BuddyGetGroup" =:: ''Int32 :-> Return ''Int32+    , "GroupGetName"  =:: ''Int32 :-> Return ''String+    , "BlistGetBuddies" =:: Return ''Ints+    , "BuddyGetAlias" =:: ''Int32 :-> Return ''String ]++main = do+  [account, buddy] <- getArgs+  dbus <- connectSession+  purple <- proxy dbus "im.pidgin.purple.PurpleService" "/im/pidgin/purple/PurpleObject"+  Just res <- replace purple "ab12cc 12 ee" "12" "ZZ"+  putStrLn res+  Just acc <- accountsFind purple account "prpl-jabber"+  Just buddiesL <- blistGetBuddies purple+  buddies <- forM buddiesL $ \buddy -> do+                    Just name <- buddyGetAlias purple buddy+                    return (name, buddy)+  let buddiesMap = M.fromList buddies+  let Just juick = M.lookup buddy buddiesMap+  Just grp <- buddyGetGroup purple juick+  Just grpName <- groupGetName purple grp+  putStrLn $ buddy ++ "'s group: " ++ show grpName+
+ dbus-th.cabal view
@@ -0,0 +1,30 @@+-- Initial dbus-th.cabal generated by cabal init.  For further +-- documentation, see http://haskell.org/cabal/users-guide/++name:                dbus-th+version:             0.1.0.0+synopsis:            TemplateHaskell generator of DBus bindings+description:         This package provides functions to easily generate bindings for+                     DBus functions. See Test.hs for examples.+license:             BSD3+license-file:        LICENSE+author:              IlyaPortnov+maintainer:          portnov84@rambler.ru+-- copyright:           +category:            Network+build-type:          Simple+cabal-version:       >=1.8+extra-source-files:  Test.hs++library+  exposed-modules:     DBus.TH+  -- other-modules:       +  build-depends:       base > 4 && < 5, containers ==0.4.*,+                       syb >= 0.3.6,+                       dbus-core ==0.9.*,+                       template-haskell >=2.6, text ==0.11.*++Source-repository head+  type:     git+  location: git://home.iportnov.ru/dbus-th.git+