--------------------------------------------------------------------------------
-- SARIF implementation for Haskell
--------------------------------------------------------------------------------
-- This source code is licensed under the MIT license found in the LICENSE    --
-- file in the root directory of this source tree.                            --
--------------------------------------------------------------------------------

-- | Provides the `ReportingDescriptor` type, which is essentially used to
-- represent descriptions of rules that a static analysis tool has applied.
module Data.SARIF.ReportingDescriptor (
    ReportingConfiguration(..),
    defaultReportingConfiguration,
    ReportingDescriptor(..),
    defaultReportingDescriptor
) where

--------------------------------------------------------------------------------

import Data.Aeson.Optional
import qualified Data.Map.Lazy as M
import Data.Text

import Data.SARIF.Level
import Data.SARIF.MultiformatMessageString

--------------------------------------------------------------------------------

-- | Represents default configurations for `ReportingDescriptor` values. That is
-- properties which may be overriden by individual results.
newtype ReportingConfiguration = MkReportingConfiguration {
    -- | The default severity of the reporting descriptor.
    ReportingConfiguration -> Maybe Level
rcLevel :: Maybe Level
} deriving (ReportingConfiguration -> ReportingConfiguration -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: ReportingConfiguration -> ReportingConfiguration -> Bool
$c/= :: ReportingConfiguration -> ReportingConfiguration -> Bool
== :: ReportingConfiguration -> ReportingConfiguration -> Bool
$c== :: ReportingConfiguration -> ReportingConfiguration -> Bool
Eq, Int -> ReportingConfiguration -> ShowS
[ReportingConfiguration] -> ShowS
ReportingConfiguration -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ReportingConfiguration] -> ShowS
$cshowList :: [ReportingConfiguration] -> ShowS
show :: ReportingConfiguration -> String
$cshow :: ReportingConfiguration -> String
showsPrec :: Int -> ReportingConfiguration -> ShowS
$cshowsPrec :: Int -> ReportingConfiguration -> ShowS
Show)

instance ToJSON ReportingConfiguration where
    toJSON :: ReportingConfiguration -> Value
toJSON MkReportingConfiguration{Maybe Level
rcLevel :: Maybe Level
rcLevel :: ReportingConfiguration -> Maybe Level
..} = [Maybe Pair] -> Value
object
        [ Key
"level" forall a. ToJSON a => Key -> Maybe a -> Maybe Pair
.=? Maybe Level
rcLevel
        ]
instance FromJSON ReportingConfiguration where
    parseJSON :: Value -> Parser ReportingConfiguration
parseJSON = forall a. String -> (Object -> Parser a) -> Value -> Parser a
withObject String
"ReportingConfiguration" forall a b. (a -> b) -> a -> b
$ \Object
obj ->
        Maybe Level -> ReportingConfiguration
MkReportingConfiguration forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Object
obj forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"level"

-- | `defaultReportingConfiguration` is a default
-- `ReportingConfiguration` value.
defaultReportingConfiguration :: ReportingConfiguration
defaultReportingConfiguration :: ReportingConfiguration
defaultReportingConfiguration = MkReportingConfiguration{
    rcLevel :: Maybe Level
rcLevel = forall a. Maybe a
Nothing
}

-- | Represents rules that a static analysis tool
data ReportingDescriptor = MkReportingDescriptor {
    -- | The unique ID of the rule.
    ReportingDescriptor -> Text
rdId :: Text,
    -- | A friendly name for the rule, which should be one word in
    -- upper camel case.
    ReportingDescriptor -> Maybe Text
rdName :: Maybe Text,
    -- | A short description for the rule, which may contain spaces
    -- and symbols.
    ReportingDescriptor -> Maybe MultiformatMessageString
rdShortDescription :: Maybe MultiformatMessageString,
    -- | The full description.
    ReportingDescriptor -> Maybe MultiformatMessageString
rdFullDescription :: Maybe MultiformatMessageString,
    -- | A URL to some help for this rule.
    ReportingDescriptor -> Maybe Text
rdHelpUri :: Maybe Text,
    -- | A recommendation for what to do in order to resolve an occurrence
    -- of this rule.
    ReportingDescriptor -> Maybe MultiformatMessageString
rdHelp :: Maybe MultiformatMessageString,
    -- | The default reporting configuration for the rule.
    ReportingDescriptor -> Maybe ReportingConfiguration
rdDefaultConfiguration :: Maybe ReportingConfiguration,
    -- | Extra properties for this rule.
    ReportingDescriptor -> Map Text Value
rdProperties :: M.Map Text Value
} deriving (ReportingDescriptor -> ReportingDescriptor -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: ReportingDescriptor -> ReportingDescriptor -> Bool
$c/= :: ReportingDescriptor -> ReportingDescriptor -> Bool
== :: ReportingDescriptor -> ReportingDescriptor -> Bool
$c== :: ReportingDescriptor -> ReportingDescriptor -> Bool
Eq, Int -> ReportingDescriptor -> ShowS
[ReportingDescriptor] -> ShowS
ReportingDescriptor -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ReportingDescriptor] -> ShowS
$cshowList :: [ReportingDescriptor] -> ShowS
show :: ReportingDescriptor -> String
$cshow :: ReportingDescriptor -> String
showsPrec :: Int -> ReportingDescriptor -> ShowS
$cshowsPrec :: Int -> ReportingDescriptor -> ShowS
Show)

instance ToJSON ReportingDescriptor where
    toJSON :: ReportingDescriptor -> Value
toJSON MkReportingDescriptor{Maybe Text
Maybe MultiformatMessageString
Maybe ReportingConfiguration
Text
Map Text Value
rdProperties :: Map Text Value
rdDefaultConfiguration :: Maybe ReportingConfiguration
rdHelp :: Maybe MultiformatMessageString
rdHelpUri :: Maybe Text
rdFullDescription :: Maybe MultiformatMessageString
rdShortDescription :: Maybe MultiformatMessageString
rdName :: Maybe Text
rdId :: Text
rdProperties :: ReportingDescriptor -> Map Text Value
rdDefaultConfiguration :: ReportingDescriptor -> Maybe ReportingConfiguration
rdHelp :: ReportingDescriptor -> Maybe MultiformatMessageString
rdHelpUri :: ReportingDescriptor -> Maybe Text
rdFullDescription :: ReportingDescriptor -> Maybe MultiformatMessageString
rdShortDescription :: ReportingDescriptor -> Maybe MultiformatMessageString
rdName :: ReportingDescriptor -> Maybe Text
rdId :: ReportingDescriptor -> Text
..} = [Maybe Pair] -> Value
object
        [ Key
"id" forall a. ToJSON a => Key -> a -> Maybe Pair
.= Text
rdId
        , Key
"name" forall a. ToJSON a => Key -> Maybe a -> Maybe Pair
.=? Maybe Text
rdName
        , Key
"shortDescription" forall a. ToJSON a => Key -> Maybe a -> Maybe Pair
.=? Maybe MultiformatMessageString
rdShortDescription
        , Key
"fullDescription" forall a. ToJSON a => Key -> Maybe a -> Maybe Pair
.=? Maybe MultiformatMessageString
rdFullDescription
        , Key
"helpUri" forall a. ToJSON a => Key -> Maybe a -> Maybe Pair
.=? Maybe Text
rdHelpUri
        , Key
"help" forall a. ToJSON a => Key -> Maybe a -> Maybe Pair
.=? Maybe MultiformatMessageString
rdHelp
        , Key
"defaultConfiguration" forall a. ToJSON a => Key -> Maybe a -> Maybe Pair
.=? Maybe ReportingConfiguration
rdDefaultConfiguration
        , Key
"properties" forall a. ToJSON a => Key -> a -> Maybe Pair
.= Map Text Value
rdProperties
        ]

instance FromJSON ReportingDescriptor where
    parseJSON :: Value -> Parser ReportingDescriptor
parseJSON = forall a. String -> (Object -> Parser a) -> Value -> Parser a
withObject String
"ReportingDescriptor" forall a b. (a -> b) -> a -> b
$ \Object
obj ->
        Text
-> Maybe Text
-> Maybe MultiformatMessageString
-> Maybe MultiformatMessageString
-> Maybe Text
-> Maybe MultiformatMessageString
-> Maybe ReportingConfiguration
-> Map Text Value
-> ReportingDescriptor
MkReportingDescriptor forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Object
obj forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"id"
                              forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
obj forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"name"
                              forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
obj forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"shortDescription"
                              forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
obj forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"fullDescription"
                              forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
obj forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"helpUri"
                              forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
obj forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"help"
                              forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
obj forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"defaultConfiguration"
                              forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
obj forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"properties" forall a. Parser (Maybe a) -> a -> Parser a
.!= forall k a. Map k a
M.empty

-- | `defaultReportingDescriptor` @id@ constructs a default
-- `ReportingDescriptor` with the given @id@, which must be unique.
defaultReportingDescriptor :: Text -> ReportingDescriptor
defaultReportingDescriptor :: Text -> ReportingDescriptor
defaultReportingDescriptor Text
ident = MkReportingDescriptor{
    rdId :: Text
rdId = Text
ident,
    rdName :: Maybe Text
rdName = forall a. Maybe a
Nothing,
    rdShortDescription :: Maybe MultiformatMessageString
rdShortDescription = forall a. Maybe a
Nothing,
    rdFullDescription :: Maybe MultiformatMessageString
rdFullDescription = forall a. Maybe a
Nothing,
    rdHelpUri :: Maybe Text
rdHelpUri = forall a. Maybe a
Nothing,
    rdHelp :: Maybe MultiformatMessageString
rdHelp = forall a. Maybe a
Nothing,
    rdDefaultConfiguration :: Maybe ReportingConfiguration
rdDefaultConfiguration = forall a. Maybe a
Nothing,
    rdProperties :: Map Text Value
rdProperties = forall k a. Map k a
M.empty
}

--------------------------------------------------------------------------------