1
1
mirror of https://github.com/github/semantic.git synced 2024-12-29 09:55:52 +03:00

Define Unmarshal instances for Range, Span, and Location.

This commit is contained in:
Rob Rix 2019-09-19 15:12:22 -04:00
parent 53d84e0150
commit 1597d9d5d2
No known key found for this signature in database
GPG Key ID: F188A01508EA1CF7
3 changed files with 32 additions and 10 deletions

View File

@ -5,12 +5,17 @@ module Data.Location
, Range(..)
) where
import Control.Applicative (liftA2)
import Data.Range
import Data.Span
import GHC.Generics (Generic)
import TreeSitter.Unmarshal
data Location = Location
{ locationByteRange :: {-# UNPACK #-} !Range
, locationSpan :: {-# UNPACK #-} !Span
}
deriving (Eq, Generic, Ord, Show)
instance Unmarshal Location where
unmarshalNodes = liftA2 Location <$> unmarshalNodes <*> unmarshalNodes

View File

@ -7,6 +7,8 @@ module Data.Range
) where
import GHC.Generics (Generic)
import TreeSitter.Node
import TreeSitter.Unmarshal
-- | A half-open interval of integers, defined by start & end indices.
data Range = Range { start :: {-# UNPACK #-} !Int, end :: {-# UNPACK #-} !Int }
@ -24,13 +26,20 @@ subtractRange :: Range -> Range -> Range
subtractRange range1 range2 = Range (start range1) (end range1 - rangeLength (Range (start range2) (max (end range1) (end range2))))
-- Instances
-- $
-- prop> a <> (b <> c) === (a <> b) <> (c :: Range)
instance Semigroup Range where
Range start1 end1 <> Range start2 end2 = Range (min start1 start2) (max end1 end2)
instance Unmarshal Range where
unmarshalNodes _ = do
node <- peekNode
case node of
Just node -> do
let start = fromIntegral (nodeStartByte node)
end = fromIntegral (nodeEndByte node)
pure (Range start end)
Nothing -> fail "expected a node but didn't get one"
-- $setup
-- >>> import Test.QuickCheck

View File

@ -7,15 +7,14 @@ module Data.Span
import Data.Aeson ((.=))
import qualified Data.Aeson as A
import GHC.Generics (Generic)
import TreeSitter.Node
import TreeSitter.Unmarshal
data Span = Span
{ spanStart :: {-# UNPACK #-} !Pos
, spanEnd :: {-# UNPACK #-} !Pos
}
deriving (Eq, Ord, Generic)
instance Show Span where
showsPrec _ s = shows (spanStart s) . showString ".." . shows (spanEnd s)
deriving (Eq, Ord, Generic, Show)
instance A.ToJSON Span where
toJSON s = A.object
@ -23,14 +22,23 @@ instance A.ToJSON Span where
, "end" .= spanEnd s
]
instance Unmarshal Span where
unmarshalNodes _ = do
node <- peekNode
case node of
Just node -> do
let spanStart = pointToPos (nodeStartPoint node)
spanEnd = pointToPos (nodeEndPoint node)
pure (Span spanStart spanEnd)
Nothing -> fail "expected a node but didn't get one"
where pointToPos (TSPoint line column) = Pos (fromIntegral line) (fromIntegral column)
data Pos = Pos
{ posLine :: {-# UNPACK #-} !Int
, posColumn :: {-# UNPACK #-} !Int
}
deriving (Eq, Ord, Generic)
instance Show Pos where
showsPrec _ p = showChar '[' . shows (posLine p) . showString ", " . shows (posColumn p) . showChar ']'
deriving (Eq, Ord, Generic, Show)
instance A.ToJSON Pos where
toJSON p = A.toJSON [posLine p, posColumn p]