xeno 0.2 → 0.3
raw patch · 7 files changed
+72/−17 lines, 7 files
Files
- CHANGELOG.markdown +3/−0
- CONTRIBUTORS.md +12/−0
- README.md +6/−1
- src/Xeno/DOM.hs +11/−3
- src/Xeno/SAX.hs +20/−4
- test/Main.hs +14/−6
- xeno.cabal +6/−3
CHANGELOG.markdown view
@@ -1,2 +1,5 @@+0.2+Added CDATA support (Rembane) + 0.1 First Hackage release
+ CONTRIBUTORS.md view
@@ -0,0 +1,12 @@+# Contributors++Original author : Chris Done ( chrisdone )++Current maintainer : Marco Zocca ( ocramz )++## In chronological order :++Andreas Ekeroot ( Rembane )+Kirill Zaborsky ( qrilka )++
README.md view
@@ -16,7 +16,7 @@ [cheats like Hexml does](http://neilmitchell.blogspot.co.uk/2016/12/new-xml-parser-hexml.html) (doesn't expand entities, or most of the XML standard). * It's written in pure Haskell.-* CDATA is supported now.+* CDATA is supported as of version 0.2. ## Performance goals@@ -187,3 +187,8 @@ The `process` is marked as INLINE, which means use-sites of it will inline, and your particular monad's type will be potentially erased for great performance.+++## Contributors++See CONTRIBUTORS.md
src/Xeno/DOM.hs view
@@ -126,10 +126,18 @@ case spork node of Left e -> Left e Right r ->- case r ! 0 of- 0x00 -> Right (Node str 0 r)- _ -> Left XenoExpectRootNode+ case findRootNode r of+ Just n -> Right n+ Nothing -> Left XenoExpectRootNode where+ findRootNode r = go 0+ where+ go n = case r UV.!? n of+ Just 0x0 -> Just (Node str n r)+ -- skipping text assuming that it contains only white space+ -- characters+ Just 0x1 -> go (n+3)+ _ -> Nothing node = runST (do nil <- UMV.new 1000
src/Xeno/SAX.hs view
@@ -262,10 +262,17 @@ -- | Basically @findIndex (not . isNameChar)@, but doesn't allocate. parseName :: ByteString -> Int -> Int parseName str index =+ if not (isNameChar1 (s_index str index))+ then index+ else parseName' str (index + 1)++-- | Basically @findIndex (not . isNameChar)@, but doesn't allocate.+parseName' :: ByteString -> Int -> Int+parseName' str index = if not (isNameChar (s_index str index)) then index- else parseName str (index + 1)-{-# INLINE parseName #-}+ else parseName' str (index + 1)+{-# INLINE parseName' #-} -- | Get index of an element starting from offset. elemIndexFrom :: Word8 -> ByteString -> Int -> Maybe Int@@ -282,10 +289,19 @@ isSpaceChar c = c == 32 || (c <= 10 && c >= 9) || c == 13 {-# INLINE isSpaceChar #-} --- | Is the character a valid tag name constituent?+-- | Is the character a valid first tag/attribute name constituent?+-- 'a'-'z', 'A'-'Z', '_', ':'+isNameChar1 :: Word8 -> Bool+isNameChar1 c =+ (c >= 97 && c <= 122) || (c >= 65 && c <= 90) || c == 95 || c == 58+{-# INLINE isNameChar1 #-}++-- | Is the character a valid tag/attribute name constituent?+-- isNameChar1 + '-', '.', '0'-'9' isNameChar :: Word8 -> Bool isNameChar c =- (c >= 97 && c <= 122) || (c >= 65 && c <= 90) || c == 95 || c == 45 || c == 58+ (c >= 97 && c <= 122) || (c >= 65 && c <= 90) || c == 95 || c == 58 ||+ c == 45 || c == 46 || (c >= 48 && c <= 57) {-# INLINE isNameChar #-} -- | Char for '\''.
test/Main.hs view
@@ -9,12 +9,7 @@ import Xeno.SAX import Xeno.DOM import Xeno.Types--- import Control.Monad.Catch -import Data.Either---- main = print "hello!"- main :: IO () main = hspec spec @@ -24,7 +19,7 @@ "hexml tests" (do mapM_ (\(v, i) -> it (show i) (shouldBe (Xeno.SAX.validate i) v))- hexml_examples_sax+ (hexml_examples_sax ++ extra_examples_sax) mapM_ (\(v, i) -> it (show i) (shouldBe (either (Left . show) (Right . id) (contents <$> Xeno.DOM.parse i)) v)) cdata_tests@@ -41,6 +36,12 @@ (shouldBe (attributes (head (children $ fromRightE doc))) [("id", "1"), ("extra", "2")])++ it "xml prologue test" $ do+ let docWithPrologue = "<?xml version=\"1.1\"?>\n<greeting>Hello, world!</greeting>"+ parsedRoot = fromRightE $ Xeno.DOM.parse docWithPrologue+ name parsedRoot `shouldBe` "greeting"+ -- If this works without crashing we're happy. let nsdoc = "<ns:tag os:attr=\"Namespaced attribute value\">Content.</ns:tag>" it@@ -59,6 +60,13 @@ ,(True, "<test></more>") -- SAX doesn't care about tag balancing ,(False, "<test") ,(True, "<?xml version=\"1.1\"?>\n<greeting>Hello, world!</greeting>")+ ]++extra_examples_sax :: [(Bool, ByteString)]+extra_examples_sax =+ [(True, "<some-example/>")+ ,(True, "<a numeric1=\"attribute\"/>")+ ,(True, "<also.a.dot></also.a.dot>") ] -- | We want to make sure that the parser doesn't jump out of the CDATA
xeno.cabal view
@@ -1,5 +1,5 @@ name: xeno-version: 0.2+version: 0.3 synopsis: A fast event-based XML parser in pure Haskell description: Please see README.md build-type: Simple@@ -12,7 +12,8 @@ maintainer: Marco Zocca (zocca.marco gmail) tested-with: GHC == 8.0.1 extra-source-files: README.md- CHANGELOG.markdown + CHANGELOG.markdown+ CONTRIBUTORS.md source-repository head type: git@@ -34,6 +35,7 @@ default-language: Haskell2010 test-suite xeno-test+ type: exitcode-stdio-1.0 hs-source-dirs: test main-is: Main.hs@@ -50,7 +52,8 @@ build-depends: libxml ghc-options: -Wall -threaded -rtsopts -with-rtsopts=-N -O2 if flag(libxml2)- ghc-options: -DLIBXML2+ cpp-options: -DLIBXML2 + -- ghc-options: -DLIBXML2 -- Hackage started complaining about this default-language: Haskell2010 benchmark xeno-memory-bench