on master help sign in
Interface improvements. Includes simple JMacro support.
commita93009850dbe0a9b89b934a2d6a0abf19520f146 authorHamish Mackenzie <Hamish.K.Mackenzie@googlemail.com> dateWed 26 Dec 2012, 19:05 (14 years ago) parent266fd49
6 files changed+161−71
jsc.cabal+10−10 src/Language/Javascript/JSC.hs+6−4 src/Language/Javascript/JSC/JMacro.hs+29 src/Language/Javascript/JSC/Monad.hs+3−12 src/Language/Javascript/JSC/Object.hs+90−36 src/Language/Javascript/JSC/Value.hs+23−9
jsc.cabal+10−10
@@ -3,19 +3,19 @@ Version: 0.0.1
33Synopsis: High level interface for webkit-javascriptcore
44Description: High level interface for JavaScriptCore module from webkitgtk
55License: MIT
6−License-file: LICENSE
7−Author: Hamish Mackenzie
6+License-file: LICENSE
7+Author: Hamish Mackenzie
88Maintainer: Hamish Mackenzie <Hamish.K.Mackenzie@googlemail.com>
99Build-Type: Custom
1010Cabal-Version: >= 1.8
1111
1212Library
13+ build-depends: template-haskell -any, base -any,
14+ text >=0.11.2.3 && <0.12, transformers >=0.3.0.0 && <0.4,
15+ webkit-javascriptcore >=0.0.0.999 && <0.1, jmacro >=0.6.3 && <0.7
16+ exposed-modules: Language.Javascript.JSC.JMacro
17+ Language.Javascript.JSC.Object Language.Javascript.JSC
18+ Language.Javascript.JSC.Value Language.Javascript.JSC.Monad
19+ exposed: True
20+ buildable: True
1321 hs-source-dirs: src
14− build-depends: base -any, text >=0.11.2.3 && <0.12,
15− transformers >=0.3.0.0 && <0.4,
16− webkit-javascriptcore >=0.0.0.999 && <0.1
17− exposed-modules:
18− Language.Javascript.JSC.Object
19− Language.Javascript.JSC
20− Language.Javascript.JSC.Value
21− Language.Javascript.JSC.Monad
src/Language/Javascript/JSC.hs+6−4
@@ -1,10 +1,12 @@
11{-# LANGUAGE ForeignFunctionInterface
22 , TypeSynonymInstances
33 , FlexibleInstances
4− , DeriveDataTypeable #-}
4+ , DeriveDataTypeable
5+ , TemplateHaskell
6+ , QuasiQuotes #-}
57-----------------------------------------------------------------------------
68--
7−-- Module : Graphics.UI.Gtk.WebKit.JavaScriptCore.JSC
9+-- Module : Language.Javascript.JSC
810-- Copyright : (c) Hamish Mackenzie
911-- License : MIT
1012--
@@ -18,6 +20,7 @@ module Language.Javascript.JSC (
1820 module Language.Javascript.JSC.Monad
1921 , module Language.Javascript.JSC.Value
2022 , module Language.Javascript.JSC.Object
23+ , module Language.Javascript.JSC.JMacro
2124
2225 , evaluateScript
2326 , eval
@@ -26,6 +29,7 @@ module Language.Javascript.JSC (
2629import Language.Javascript.JSC.Monad
2730import Language.Javascript.JSC.Value
2831import Language.Javascript.JSC.Object
32+import Language.Javascript.JSC.JMacro
2933
3034import Control.Monad.Trans.Reader (ask)
3135import Control.Monad.IO.Class (MonadIO(..))
@@ -51,5 +55,3 @@ evaluateScript script this url line exception = do
5155
5256eval script = rethrow $ evaluateScript script nullPtr (nullPtr::JSStringRef) 1
5357
54−
55−
src/Language/Javascript/JSC/JMacro.hsnew file+29
@@ -0,0 +1,29 @@
1+{-# LANGUAGE TemplateHaskell, QuasiQuotes #-}
2+-----------------------------------------------------------------------------
3+--
4+-- Module : Language.Javascript.JSC.JMacro
5+-- Copyright : (c) Hamish Mackenzie
6+-- License : MIT
7+--
8+-- Maintainer : Hamish Mackenzie <Hamish.K.Mackenzie@googlemail.com>
9+--
10+-- |
11+--
12+-----------------------------------------------------------------------------
13+
14+module Language.Javascript.JSC.JMacro (
15+ evalJM
16+) where
17+
18+import Language.Haskell.TH.Quote (QuasiQuoter(..))
19+import Language.Haskell.TH
20+ (varE, appE, Lit(..), Exp(..), mkName, ExpQ)
21+import Language.Javascript.JMacro (jmacroE, renderJs)
22+
23+evalJM :: QuasiQuoter
24+evalJM = QuasiQuoter {quoteExp = quoteEvalJM}
25+
26+quoteEvalJM :: String -> ExpQ
27+quoteEvalJM s = do
28+ appE (varE 'return) [|AppE (VarE $ mkName "Language.Javascript.JSC.eval")
29+ (LitE . StringL . show $ renderJs $(quoteExp jmacroE s))|]
src/Language/Javascript/JSC/Monad.hs+3−12
@@ -4,7 +4,7 @@
44 , DeriveDataTypeable #-}
55-----------------------------------------------------------------------------
66--
7−-- Module : Graphics.UI.Gtk.WebKit.JavaScriptCore.JSC.Monad
7+-- Module : Language.Javascript.JSC.Monad
88-- Copyright : (c) Hamish Mackenzie
99-- License : MIT
1010--
@@ -16,37 +16,28 @@
1616
1717module Language.Javascript.JSC.Monad (
1818 JSC(..)
19− , JSException(..)
19+ , JSContextRef
2020 , catch
21− , rethrow
2221) where
2322
24−import qualified Control.Exception as E (throwIO, Exception)
2523import Control.Monad.Trans.Reader (runReaderT, ask, ReaderT(..))
2624import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
2725 (JSValueRefRef, JSValueRef, JSContextRef)
28−import Data.Typeable (Typeable)
2926import Control.Monad.IO.Class (MonadIO(..))
3027import Foreign (nullPtr, alloca)
3128import Foreign.Storable (Storable(..))
3229
3330type JSC = ReaderT JSContextRef IO
3431
35−newtype JSException = JSException JSValueRef deriving (Show, Typeable)
36−
37−instance E.Exception JSException
38−
3932catch :: (JSValueRefRef -> JSC a) -> (JSValueRef -> JSC a) -> JSC a
4033catch f catcher = do
4134 gctxt <- ask
4235 liftIO . alloca $ \pexc -> flip runReaderT gctxt $ do
36+ liftIO $ poke pexc nullPtr
4337 result <- f pexc
4438 exc <- liftIO $ peek pexc
4539 if exc == nullPtr
4640 then return result
4741 else catcher exc
4842
49−rethrow :: (JSValueRefRef -> JSC a) -> JSC a
50−rethrow = flip catch $ liftIO . E.throwIO . JSException
51−
5243
src/Language/Javascript/JSC/Object.hs+90−36
@@ -5,7 +5,7 @@
55 , ScopedTypeVariables #-}
66-----------------------------------------------------------------------------
77--
8−-- Module : Graphics.UI.Gtk.WebKit.JavaScriptCore.JSC.Object
8+-- Module : Language.Javascript.JSC.Object
99-- Copyright : (c) Hamish Mackenzie
1010-- License : MIT
1111--
@@ -20,28 +20,32 @@ module Language.Javascript.JSC.Object (
2020 , objGetProperty
2121 , objCallAsFunction
2222 , (!)
23+ , (!!)
2324 , (#)
2425 , (<#)
2526 , new
27+ , call
2628 , function
2729 , fun
2830 , array
2931 , global
3032) where
3133
34+import Prelude hiding ((!!))
3235import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
3336 (JSStringRef, JSObjectRef, JSValueRefRef, JSValueRef, JSContextRef)
34−import Foreign.C (CULong(..))
37+import Foreign.C (CUInt, CULong(..))
3538import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSObjectRef
36− (jsobjectcallasconstructor, jsobjectmakearray,
39+ (jsobjectsetpropertyatindex, jsobjectgetpropertyatindex,
40+ jsobjectcallasconstructor, jsobjectmakearray,
3741 jsobjectcallasfunction, jsobjectgetproperty, jsobjectsetproperty,
3842 JSPropertyAttributes, JSObjectCallAsFunctionCallback,
3943 jsobjectmakefunctionwithcallback)
4044import Language.Javascript.JSC.Value
4145 (valMakeUndefined, valToObject, MakeValueRef(..),
42− MakeStringRef(..), MakeArgRefs(..))
46+ MakeStringRef(..), MakeArgRefs(..), rethrow)
4347import Language.Javascript.JSC.Monad
44− (rethrow, JSC)
48+ (JSC)
4549import Control.Monad.Trans.Reader (runReaderT, ask)
4650import Control.Monad.IO.Class (MonadIO(..))
4751import Foreign (peekArray, nullPtr, withArrayLen)
@@ -66,28 +70,26 @@ instance MakeObjectRef v => MakeObjectRef (JSC v) where
6670
6771---- Property References ----
6872data JSPropRef = JSPropRef JSObjectRef JSStringRef
73+ | JSPropIndexRef JSObjectRef CUInt
6974
7075class MakePropRef this where
7176 makePropRef :: this -> JSC JSPropRef
7277
7378instance MakePropRef JSPropRef where
74− makePropRef (JSPropRef this name) = do
75− rthis <- makeObjectRef this
76− rname <- makeStringRef name
77− return (JSPropRef rthis rname)
79+ makePropRef = return
7880
7981instance MakePropRef prop => MakePropRef (JSC prop) where
80− makePropRef prop = prop >>= makePropRef
82+ makePropRef prop = prop >>= makePropRef
8183
8284instance MakeObjectRef JSPropRef where
83− makeObjectRef (JSPropRef this name) = rethrow $ objGetProperty this name
85+ makeObjectRef = objGetProperty
8486
8587instance MakeValueRef JSPropRef where
86− makeValueRef (JSPropRef this name) = rethrow $ objGetProperty this name
88+ makeValueRef = objGetProperty
8789
8890instance MakeArgRefs JSPropRef where
89− makeArgRefs (JSPropRef this name) = do
90− rarg <- rethrow $ objGetProperty this name
91+ makeArgRefs p = do
92+ rarg <- objGetProperty p
9193 return [rarg]
9294
9395---- String global scope ----
@@ -101,34 +103,74 @@ instance MakeObjectRef String where
101103 makeObjectRef name = do
102104 this <- global
103105 rname <- makeStringRef name
104− (rethrow $ objGetProperty this rname) >>= valToObject
106+ (rethrow $ objGetPropertyByName this rname) >>= valToObject
105107
106108global :: JSC JSObjectRef
107109global = ask >>= (liftIO . jscontextgetglobalobject)
108110
109−objSetProperty :: (MakeStringRef name, MakeValueRef val)
110− => JSObjectRef
111− -> name
112− -> val
113− -> JSPropertyAttributes
114− -> JSValueRefRef
115− -> JSC ()
116−objSetProperty this name val attributes exceptions = do
111+objSetPropertyByName :: (MakeStringRef name, MakeValueRef val)
112+ => JSObjectRef
113+ -> name
114+ -> val
115+ -> JSPropertyAttributes
116+ -> JSValueRefRef
117+ -> JSC ()
118+objSetPropertyByName this name val attributes exceptions = do
117119 gctxt <- ask
118120 sName <- makeStringRef name
119121 vref <- makeValueRef val
120122 liftIO $ jsobjectsetproperty gctxt this sName vref attributes exceptions
121123
122−objGetProperty :: MakeStringRef name
123− => JSObjectRef
124− -> name
125− -> JSValueRefRef
126− -> JSC JSValueRef
127−objGetProperty this name exceptions = do
124+objSetPropertyAtIndex :: (MakeValueRef val)
125+ => JSObjectRef
126+ -> CUInt
127+ -> val
128+ -> JSValueRefRef
129+ -> JSC ()
130+objSetPropertyAtIndex this index val exceptions = do
131+ gctxt <- ask
132+ vref <- makeValueRef val
133+ liftIO $ jsobjectsetpropertyatindex gctxt this index vref exceptions
134+
135+objSetProperty :: (MakeValueRef val)
136+ => JSPropRef
137+ -> val
138+ -> JSC ()
139+objSetProperty (JSPropRef this name ) val = rethrow $ objSetPropertyByName this name val 0
140+objSetProperty (JSPropIndexRef this index) val = rethrow $ objSetPropertyAtIndex this index val
141+
142+objGetPropertyByName :: MakeStringRef name
143+ => JSObjectRef
144+ -> name
145+ -> JSValueRefRef
146+ -> JSC JSValueRef
147+objGetPropertyByName this name exceptions = do
128148 gctxt <- ask
129149 sName <- makeStringRef name
130150 liftIO $ jsobjectgetproperty gctxt this sName exceptions
131151
152+objGetPropertyAtIndex :: JSObjectRef
153+ -> CUInt
154+ -> JSValueRefRef
155+ -> JSC JSValueRef
156+objGetPropertyAtIndex this index exceptions = do
157+ gctxt <- ask
158+ liftIO $ jsobjectgetpropertyatindex gctxt this index exceptions
159+
160+objGetProperty :: JSPropRef
161+ -> JSC JSValueRef
162+objGetProperty (JSPropRef this name ) = rethrow $ objGetPropertyByName this name
163+objGetProperty (JSPropIndexRef this index) = rethrow $ objGetPropertyAtIndex this index
164+
165+objGetProperty' :: JSPropRef
166+ -> JSC (JSObjectRef, JSValueRef)
167+objGetProperty' (JSPropRef this name) = do
168+ p <- rethrow $ objGetPropertyByName this name
169+ return (this, p)
170+objGetProperty' (JSPropIndexRef this index) = do
171+ p <- rethrow $ objGetPropertyAtIndex this index
172+ return (this, p)
173+
132174objCallAsFunction :: MakeArgRefs args
133175 => JSObjectRef
134176 -> JSObjectRef
@@ -158,18 +200,24 @@ this ! name = do
158200 rname <- makeStringRef name
159201 return (JSPropRef rthis rname)
160202
203+(!!) :: (MakeObjectRef this) => this -> CUInt -> JSC JSPropRef
204+this !! index = do
205+ rthis <- makeObjectRef this
206+ return (JSPropIndexRef rthis index)
207+
161208(#) :: (MakePropRef prop, MakeArgRefs args)
162209 => prop -> args -> JSC JSValueRef
163210prop # args = do
164− (JSPropRef this name) <- makePropRef prop
165− f <- (rethrow $ objGetProperty this name) >>= valToObject
211+ rprop <- makePropRef prop
212+ (this, f) <- objGetProperty' rprop
166213 rethrow $ objCallAsFunction f this args
167214
168215(<#) :: (MakePropRef prop, MakeValueRef val)
169− => prop -> val -> JSC ()
216+ => prop -> val -> JSC JSPropRef
170217prop <# val = do
171− (JSPropRef this name) <- makePropRef prop
172− rethrow $ objSetProperty this name val 0
218+ p <- makePropRef prop
219+ objSetProperty p val
220+ return p
173221
174222new :: (MakeObjectRef constructor, MakeArgRefs args)
175223 => constructor -> args -> JSC JSValueRef
@@ -177,6 +225,13 @@ new constructor args = do
177225 f <- makeObjectRef constructor
178226 rethrow $ objCallAsConstructor f args
179227
228+call :: (MakeObjectRef function, MakeObjectRef this, MakeArgRefs args)
229+ => function -> this -> args -> JSC JSValueRef
230+call function this args = do
231+ rfunction <- makeObjectRef function
232+ rthis <- makeObjectRef this
233+ rethrow $ objCallAsFunction rfunction rthis args
234+
180235type JSObjectCallAsFunctionCallback' =
181236 JSContextRef
182237 -> JSValueRef
@@ -228,7 +283,7 @@ makeArray args exceptions = do
228283 liftIO $ withArrayLen rargs $ \ len ptr ->
229284 jsobjectmakearray gctxt (fromIntegral len) ptr exceptions
230285
231−array :: MakeArgRefs args => args -> JSC JSValueRef
286+array :: MakeArgRefs args => args -> JSC JSObjectRef
232287array = rethrow . makeArray
233288
234289
@@ -250,6 +305,5 @@ array = rethrow . makeArray
250305
251306
252307
253−
254308
255309
src/Language/Javascript/JSC/Value.hs+23−9
@@ -4,7 +4,7 @@
44 , DeriveDataTypeable #-}
55-----------------------------------------------------------------------------
66--
7−-- Module : Graphics.UI.Gtk.WebKit.JavaScriptCore.JSC.Value
7+-- Module : Language.Javascript.JSC.Value
88-- Copyright : (c) Hamish Mackenzie
99-- License : MIT
1010--
@@ -36,6 +36,8 @@ module Language.Javascript.JSC.Value (
3636
3737 , valToText
3838
39+ , rethrow
40+
3941 , MakeValueRef(..)
4042 , MakeStringRef(..)
4143 , MakeArgRefs(..)
@@ -52,8 +54,8 @@ module Language.Javascript.JSC.Value (
5254) where
5355
5456import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
55− (JSObjectRef, JSStringRef, JSValueRef)
56−import Language.Javascript.JSC.Monad (rethrow, JSC)
57+ (JSValueRefRef, JSObjectRef, JSStringRef, JSValueRef)
58+import Language.Javascript.JSC.Monad (JSC, catch)
5759import Control.Monad.Trans.Reader (ask)
5860import Control.Monad.IO.Class (MonadIO, MonadIO(..))
5961import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSValueRef
@@ -70,6 +72,8 @@ import Data.Text.Foreign (useAsPtr)
7072import Control.Applicative ((<$>))
7173import Data.Text (Text)
7274import qualified Data.Text as T (pack)
75+import qualified Control.Exception as E (throwIO, Exception)
76+import Data.Typeable (Typeable)
7377
7478data JSNull = JSNull
7579type JSUndefined = ()
@@ -118,6 +122,15 @@ textToStr text = do
118122valToText :: JSValueRef -> JSC Text
119123valToText jsvar = valToStr jsvar >>= strToText
120124
125+data JSException = JSException String JSValueRef deriving (Show, Typeable)
126+
127+instance E.Exception JSException
128+
129+rethrow :: (JSValueRefRef -> JSC a) -> JSC a
130+rethrow f = f `catch` \e -> do
131+ s <- deRefVal e
132+ liftIO . E.throwIO $ JSException (show s) e
133+
121134class MakeValueRef a where
122135 makeValueRef :: a -> JSC JSValueRef
123136
@@ -129,7 +142,7 @@ class MakeArgRefs this where
129142 makeArgRefs :: this -> JSC [JSValueRef]
130143
131144instance MakeArgRefs arg => MakeArgRefs (JSC arg) where
132− makeArgRefs arg = arg >>= makeArgRefs
145+ makeArgRefs arg = arg >>= makeArgRefs
133146
134147instance MakeValueRef arg => MakeArgRefs [arg] where
135148 makeArgRefs = mapM makeValueRef
@@ -156,7 +169,7 @@ instance (MakeValueRef arg1, MakeValueRef arg2, MakeValueRef arg3, MakeValueRef
156169 rarg2 <- makeValueRef arg2
157170 rarg3 <- makeValueRef arg3
158171 rarg4 <- makeValueRef arg4
159− return [rarg1, rarg2, rarg3, rarg3]
172+ return [rarg1, rarg2, rarg3, rarg4]
160173
161174instance (MakeValueRef arg1, MakeValueRef arg2, MakeValueRef arg3, MakeValueRef arg4, MakeValueRef arg5) => MakeArgRefs (arg1, arg2, arg3, arg4, arg5) where
162175 makeArgRefs (arg1, arg2, arg3, arg4, arg5) = do
@@ -165,7 +178,7 @@ instance (MakeValueRef arg1, MakeValueRef arg2, MakeValueRef arg3, MakeValueRef
165178 rarg3 <- makeValueRef arg3
166179 rarg4 <- makeValueRef arg4
167180 rarg5 <- makeValueRef arg5
168− return [rarg1, rarg2, rarg3, rarg3, rarg5]
181+ return [rarg1, rarg2, rarg3, rarg4, rarg5]
169182
170183val :: MakeValueRef v => v -> JSC JSValueRef
171184val = makeValueRef
@@ -177,7 +190,7 @@ instance MakeArgRefs JSValueRef where
177190 makeArgRefs arg = return [arg]
178191
179192instance MakeValueRef v => MakeValueRef (JSC v) where
180− makeValueRef prop = prop >>= makeValueRef
193+ makeValueRef v = v >>= makeValueRef
181194
182195instance MakeStringRef JSStringRef where
183196 makeStringRef = return
@@ -244,9 +257,10 @@ instance MakeArgRefs Text where
244257instance MakeValueRef String where
245258 makeValueRef = valMakeString . T.pack
246259
247−deRefVal :: JSValueRef -> JSC JSValue
248−deRefVal valref = do
260+deRefVal :: MakeValueRef val => val -> JSC JSValue
261+deRefVal val = do
249262 gctxt <- ask
263+ valref <- makeValueRef val
250264 t <- liftIO $ jsvaluegettype gctxt valref
251265 case t of
252266 Kjstypenull -> return ValNull