cdp-0.0.1.0: src/CDP/Domains/Tracing.hs
{-# LANGUAGE OverloadedStrings, RecordWildCards, TupleSections #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE DeriveGeneric #-}
{-# LANGUAGE TypeFamilies #-}
{- |
= Tracing
-}
module CDP.Domains.Tracing (module CDP.Domains.Tracing) where
import Control.Applicative ((<$>))
import Control.Monad
import Control.Monad.Loops
import Control.Monad.Trans (liftIO)
import qualified Data.Map as M
import Data.Maybe
import Data.Functor.Identity
import Data.String
import qualified Data.Text as T
import qualified Data.List as List
import qualified Data.Text.IO as TI
import qualified Data.Vector as V
import Data.Aeson.Types (Parser(..))
import Data.Aeson (FromJSON (..), ToJSON (..), (.:), (.:?), (.=), (.!=), (.:!))
import qualified Data.Aeson as A
import qualified Network.HTTP.Simple as Http
import qualified Network.URI as Uri
import qualified Network.WebSockets as WS
import Control.Concurrent
import qualified Data.ByteString.Lazy as BS
import qualified Data.Map as Map
import Data.Proxy
import System.Random
import GHC.Generics
import Data.Char
import Data.Default
import CDP.Internal.Utils
import CDP.Domains.IO as IO
-- | Type 'Tracing.MemoryDumpConfig'.
-- Configuration for memory dump. Used only when "memory-infra" category is enabled.
type TracingMemoryDumpConfig = [(T.Text, T.Text)]
-- | Type 'Tracing.TraceConfig'.
data TracingTraceConfigRecordMode = TracingTraceConfigRecordModeRecordUntilFull | TracingTraceConfigRecordModeRecordContinuously | TracingTraceConfigRecordModeRecordAsMuchAsPossible | TracingTraceConfigRecordModeEchoToConsole
deriving (Ord, Eq, Show, Read)
instance FromJSON TracingTraceConfigRecordMode where
parseJSON = A.withText "TracingTraceConfigRecordMode" $ \v -> case v of
"recordUntilFull" -> pure TracingTraceConfigRecordModeRecordUntilFull
"recordContinuously" -> pure TracingTraceConfigRecordModeRecordContinuously
"recordAsMuchAsPossible" -> pure TracingTraceConfigRecordModeRecordAsMuchAsPossible
"echoToConsole" -> pure TracingTraceConfigRecordModeEchoToConsole
"_" -> fail "failed to parse TracingTraceConfigRecordMode"
instance ToJSON TracingTraceConfigRecordMode where
toJSON v = A.String $ case v of
TracingTraceConfigRecordModeRecordUntilFull -> "recordUntilFull"
TracingTraceConfigRecordModeRecordContinuously -> "recordContinuously"
TracingTraceConfigRecordModeRecordAsMuchAsPossible -> "recordAsMuchAsPossible"
TracingTraceConfigRecordModeEchoToConsole -> "echoToConsole"
data TracingTraceConfig = TracingTraceConfig
{
-- | Controls how the trace buffer stores data.
tracingTraceConfigRecordMode :: Maybe TracingTraceConfigRecordMode,
-- | Size of the trace buffer in kilobytes. If not specified or zero is passed, a default value
-- of 200 MB would be used.
tracingTraceConfigTraceBufferSizeInKb :: Maybe Double,
-- | Turns on JavaScript stack sampling.
tracingTraceConfigEnableSampling :: Maybe Bool,
-- | Turns on system tracing.
tracingTraceConfigEnableSystrace :: Maybe Bool,
-- | Turns on argument filter.
tracingTraceConfigEnableArgumentFilter :: Maybe Bool,
-- | Included category filters.
tracingTraceConfigIncludedCategories :: Maybe [T.Text],
-- | Excluded category filters.
tracingTraceConfigExcludedCategories :: Maybe [T.Text],
-- | Configuration to synthesize the delays in tracing.
tracingTraceConfigSyntheticDelays :: Maybe [T.Text],
-- | Configuration for memory dump triggers. Used only when "memory-infra" category is enabled.
tracingTraceConfigMemoryDumpConfig :: Maybe TracingMemoryDumpConfig
}
deriving (Eq, Show)
instance FromJSON TracingTraceConfig where
parseJSON = A.withObject "TracingTraceConfig" $ \o -> TracingTraceConfig
<$> o A..:? "recordMode"
<*> o A..:? "traceBufferSizeInKb"
<*> o A..:? "enableSampling"
<*> o A..:? "enableSystrace"
<*> o A..:? "enableArgumentFilter"
<*> o A..:? "includedCategories"
<*> o A..:? "excludedCategories"
<*> o A..:? "syntheticDelays"
<*> o A..:? "memoryDumpConfig"
instance ToJSON TracingTraceConfig where
toJSON p = A.object $ catMaybes [
("recordMode" A..=) <$> (tracingTraceConfigRecordMode p),
("traceBufferSizeInKb" A..=) <$> (tracingTraceConfigTraceBufferSizeInKb p),
("enableSampling" A..=) <$> (tracingTraceConfigEnableSampling p),
("enableSystrace" A..=) <$> (tracingTraceConfigEnableSystrace p),
("enableArgumentFilter" A..=) <$> (tracingTraceConfigEnableArgumentFilter p),
("includedCategories" A..=) <$> (tracingTraceConfigIncludedCategories p),
("excludedCategories" A..=) <$> (tracingTraceConfigExcludedCategories p),
("syntheticDelays" A..=) <$> (tracingTraceConfigSyntheticDelays p),
("memoryDumpConfig" A..=) <$> (tracingTraceConfigMemoryDumpConfig p)
]
-- | Type 'Tracing.StreamFormat'.
-- Data format of a trace. Can be either the legacy JSON format or the
-- protocol buffer format. Note that the JSON format will be deprecated soon.
data TracingStreamFormat = TracingStreamFormatJson | TracingStreamFormatProto
deriving (Ord, Eq, Show, Read)
instance FromJSON TracingStreamFormat where
parseJSON = A.withText "TracingStreamFormat" $ \v -> case v of
"json" -> pure TracingStreamFormatJson
"proto" -> pure TracingStreamFormatProto
"_" -> fail "failed to parse TracingStreamFormat"
instance ToJSON TracingStreamFormat where
toJSON v = A.String $ case v of
TracingStreamFormatJson -> "json"
TracingStreamFormatProto -> "proto"
-- | Type 'Tracing.StreamCompression'.
-- Compression type to use for traces returned via streams.
data TracingStreamCompression = TracingStreamCompressionNone | TracingStreamCompressionGzip
deriving (Ord, Eq, Show, Read)
instance FromJSON TracingStreamCompression where
parseJSON = A.withText "TracingStreamCompression" $ \v -> case v of
"none" -> pure TracingStreamCompressionNone
"gzip" -> pure TracingStreamCompressionGzip
"_" -> fail "failed to parse TracingStreamCompression"
instance ToJSON TracingStreamCompression where
toJSON v = A.String $ case v of
TracingStreamCompressionNone -> "none"
TracingStreamCompressionGzip -> "gzip"
-- | Type 'Tracing.MemoryDumpLevelOfDetail'.
-- Details exposed when memory request explicitly declared.
-- Keep consistent with memory_dump_request_args.h and
-- memory_instrumentation.mojom
data TracingMemoryDumpLevelOfDetail = TracingMemoryDumpLevelOfDetailBackground | TracingMemoryDumpLevelOfDetailLight | TracingMemoryDumpLevelOfDetailDetailed
deriving (Ord, Eq, Show, Read)
instance FromJSON TracingMemoryDumpLevelOfDetail where
parseJSON = A.withText "TracingMemoryDumpLevelOfDetail" $ \v -> case v of
"background" -> pure TracingMemoryDumpLevelOfDetailBackground
"light" -> pure TracingMemoryDumpLevelOfDetailLight
"detailed" -> pure TracingMemoryDumpLevelOfDetailDetailed
"_" -> fail "failed to parse TracingMemoryDumpLevelOfDetail"
instance ToJSON TracingMemoryDumpLevelOfDetail where
toJSON v = A.String $ case v of
TracingMemoryDumpLevelOfDetailBackground -> "background"
TracingMemoryDumpLevelOfDetailLight -> "light"
TracingMemoryDumpLevelOfDetailDetailed -> "detailed"
-- | Type 'Tracing.TracingBackend'.
-- Backend type to use for tracing. `chrome` uses the Chrome-integrated
-- tracing service and is supported on all platforms. `system` is only
-- supported on Chrome OS and uses the Perfetto system tracing service.
-- `auto` chooses `system` when the perfettoConfig provided to Tracing.start
-- specifies at least one non-Chrome data source; otherwise uses `chrome`.
data TracingTracingBackend = TracingTracingBackendAuto | TracingTracingBackendChrome | TracingTracingBackendSystem
deriving (Ord, Eq, Show, Read)
instance FromJSON TracingTracingBackend where
parseJSON = A.withText "TracingTracingBackend" $ \v -> case v of
"auto" -> pure TracingTracingBackendAuto
"chrome" -> pure TracingTracingBackendChrome
"system" -> pure TracingTracingBackendSystem
"_" -> fail "failed to parse TracingTracingBackend"
instance ToJSON TracingTracingBackend where
toJSON v = A.String $ case v of
TracingTracingBackendAuto -> "auto"
TracingTracingBackendChrome -> "chrome"
TracingTracingBackendSystem -> "system"
-- | Type of the 'Tracing.bufferUsage' event.
data TracingBufferUsage = TracingBufferUsage
{
-- | A number in range [0..1] that indicates the used size of event buffer as a fraction of its
-- total size.
tracingBufferUsagePercentFull :: Maybe Double,
-- | An approximate number of events in the trace log.
tracingBufferUsageEventCount :: Maybe Double,
-- | A number in range [0..1] that indicates the used size of event buffer as a fraction of its
-- total size.
tracingBufferUsageValue :: Maybe Double
}
deriving (Eq, Show)
instance FromJSON TracingBufferUsage where
parseJSON = A.withObject "TracingBufferUsage" $ \o -> TracingBufferUsage
<$> o A..:? "percentFull"
<*> o A..:? "eventCount"
<*> o A..:? "value"
instance Event TracingBufferUsage where
eventName _ = "Tracing.bufferUsage"
-- | Type of the 'Tracing.dataCollected' event.
data TracingDataCollected = TracingDataCollected
{
tracingDataCollectedValue :: [[(T.Text, T.Text)]]
}
deriving (Eq, Show)
instance FromJSON TracingDataCollected where
parseJSON = A.withObject "TracingDataCollected" $ \o -> TracingDataCollected
<$> o A..: "value"
instance Event TracingDataCollected where
eventName _ = "Tracing.dataCollected"
-- | Type of the 'Tracing.tracingComplete' event.
data TracingTracingComplete = TracingTracingComplete
{
-- | Indicates whether some trace data is known to have been lost, e.g. because the trace ring
-- buffer wrapped around.
tracingTracingCompleteDataLossOccurred :: Bool,
-- | A handle of the stream that holds resulting trace data.
tracingTracingCompleteStream :: Maybe IO.IOStreamHandle,
-- | Trace data format of returned stream.
tracingTracingCompleteTraceFormat :: Maybe TracingStreamFormat,
-- | Compression format of returned stream.
tracingTracingCompleteStreamCompression :: Maybe TracingStreamCompression
}
deriving (Eq, Show)
instance FromJSON TracingTracingComplete where
parseJSON = A.withObject "TracingTracingComplete" $ \o -> TracingTracingComplete
<$> o A..: "dataLossOccurred"
<*> o A..:? "stream"
<*> o A..:? "traceFormat"
<*> o A..:? "streamCompression"
instance Event TracingTracingComplete where
eventName _ = "Tracing.tracingComplete"
-- | Stop trace events collection.
-- | Parameters of the 'Tracing.end' command.
data PTracingEnd = PTracingEnd
deriving (Eq, Show)
pTracingEnd
:: PTracingEnd
pTracingEnd
= PTracingEnd
instance ToJSON PTracingEnd where
toJSON _ = A.Null
instance Command PTracingEnd where
type CommandResponse PTracingEnd = ()
commandName _ = "Tracing.end"
fromJSON = const . A.Success . const ()
-- | Gets supported tracing categories.
-- | Parameters of the 'Tracing.getCategories' command.
data PTracingGetCategories = PTracingGetCategories
deriving (Eq, Show)
pTracingGetCategories
:: PTracingGetCategories
pTracingGetCategories
= PTracingGetCategories
instance ToJSON PTracingGetCategories where
toJSON _ = A.Null
data TracingGetCategories = TracingGetCategories
{
-- | A list of supported tracing categories.
tracingGetCategoriesCategories :: [T.Text]
}
deriving (Eq, Show)
instance FromJSON TracingGetCategories where
parseJSON = A.withObject "TracingGetCategories" $ \o -> TracingGetCategories
<$> o A..: "categories"
instance Command PTracingGetCategories where
type CommandResponse PTracingGetCategories = TracingGetCategories
commandName _ = "Tracing.getCategories"
-- | Record a clock sync marker in the trace.
-- | Parameters of the 'Tracing.recordClockSyncMarker' command.
data PTracingRecordClockSyncMarker = PTracingRecordClockSyncMarker
{
-- | The ID of this clock sync marker
pTracingRecordClockSyncMarkerSyncId :: T.Text
}
deriving (Eq, Show)
pTracingRecordClockSyncMarker
{-
-- | The ID of this clock sync marker
-}
:: T.Text
-> PTracingRecordClockSyncMarker
pTracingRecordClockSyncMarker
arg_pTracingRecordClockSyncMarkerSyncId
= PTracingRecordClockSyncMarker
arg_pTracingRecordClockSyncMarkerSyncId
instance ToJSON PTracingRecordClockSyncMarker where
toJSON p = A.object $ catMaybes [
("syncId" A..=) <$> Just (pTracingRecordClockSyncMarkerSyncId p)
]
instance Command PTracingRecordClockSyncMarker where
type CommandResponse PTracingRecordClockSyncMarker = ()
commandName _ = "Tracing.recordClockSyncMarker"
fromJSON = const . A.Success . const ()
-- | Request a global memory dump.
-- | Parameters of the 'Tracing.requestMemoryDump' command.
data PTracingRequestMemoryDump = PTracingRequestMemoryDump
{
-- | Enables more deterministic results by forcing garbage collection
pTracingRequestMemoryDumpDeterministic :: Maybe Bool,
-- | Specifies level of details in memory dump. Defaults to "detailed".
pTracingRequestMemoryDumpLevelOfDetail :: Maybe TracingMemoryDumpLevelOfDetail
}
deriving (Eq, Show)
pTracingRequestMemoryDump
:: PTracingRequestMemoryDump
pTracingRequestMemoryDump
= PTracingRequestMemoryDump
Nothing
Nothing
instance ToJSON PTracingRequestMemoryDump where
toJSON p = A.object $ catMaybes [
("deterministic" A..=) <$> (pTracingRequestMemoryDumpDeterministic p),
("levelOfDetail" A..=) <$> (pTracingRequestMemoryDumpLevelOfDetail p)
]
data TracingRequestMemoryDump = TracingRequestMemoryDump
{
-- | GUID of the resulting global memory dump.
tracingRequestMemoryDumpDumpGuid :: T.Text,
-- | True iff the global memory dump succeeded.
tracingRequestMemoryDumpSuccess :: Bool
}
deriving (Eq, Show)
instance FromJSON TracingRequestMemoryDump where
parseJSON = A.withObject "TracingRequestMemoryDump" $ \o -> TracingRequestMemoryDump
<$> o A..: "dumpGuid"
<*> o A..: "success"
instance Command PTracingRequestMemoryDump where
type CommandResponse PTracingRequestMemoryDump = TracingRequestMemoryDump
commandName _ = "Tracing.requestMemoryDump"
-- | Start trace events collection.
-- | Parameters of the 'Tracing.start' command.
data PTracingStartTransferMode = PTracingStartTransferModeReportEvents | PTracingStartTransferModeReturnAsStream
deriving (Ord, Eq, Show, Read)
instance FromJSON PTracingStartTransferMode where
parseJSON = A.withText "PTracingStartTransferMode" $ \v -> case v of
"ReportEvents" -> pure PTracingStartTransferModeReportEvents
"ReturnAsStream" -> pure PTracingStartTransferModeReturnAsStream
"_" -> fail "failed to parse PTracingStartTransferMode"
instance ToJSON PTracingStartTransferMode where
toJSON v = A.String $ case v of
PTracingStartTransferModeReportEvents -> "ReportEvents"
PTracingStartTransferModeReturnAsStream -> "ReturnAsStream"
data PTracingStart = PTracingStart
{
-- | If set, the agent will issue bufferUsage events at this interval, specified in milliseconds
pTracingStartBufferUsageReportingInterval :: Maybe Double,
-- | Whether to report trace events as series of dataCollected events or to save trace to a
-- stream (defaults to `ReportEvents`).
pTracingStartTransferMode :: Maybe PTracingStartTransferMode,
-- | Trace data format to use. This only applies when using `ReturnAsStream`
-- transfer mode (defaults to `json`).
pTracingStartStreamFormat :: Maybe TracingStreamFormat,
-- | Compression format to use. This only applies when using `ReturnAsStream`
-- transfer mode (defaults to `none`)
pTracingStartStreamCompression :: Maybe TracingStreamCompression,
pTracingStartTraceConfig :: Maybe TracingTraceConfig,
-- | Base64-encoded serialized perfetto.protos.TraceConfig protobuf message
-- When specified, the parameters `categories`, `options`, `traceConfig`
-- are ignored. (Encoded as a base64 string when passed over JSON)
pTracingStartPerfettoConfig :: Maybe T.Text,
-- | Backend type (defaults to `auto`)
pTracingStartTracingBackend :: Maybe TracingTracingBackend
}
deriving (Eq, Show)
pTracingStart
:: PTracingStart
pTracingStart
= PTracingStart
Nothing
Nothing
Nothing
Nothing
Nothing
Nothing
Nothing
instance ToJSON PTracingStart where
toJSON p = A.object $ catMaybes [
("bufferUsageReportingInterval" A..=) <$> (pTracingStartBufferUsageReportingInterval p),
("transferMode" A..=) <$> (pTracingStartTransferMode p),
("streamFormat" A..=) <$> (pTracingStartStreamFormat p),
("streamCompression" A..=) <$> (pTracingStartStreamCompression p),
("traceConfig" A..=) <$> (pTracingStartTraceConfig p),
("perfettoConfig" A..=) <$> (pTracingStartPerfettoConfig p),
("tracingBackend" A..=) <$> (pTracingStartTracingBackend p)
]
instance Command PTracingStart where
type CommandResponse PTracingStart = ()
commandName _ = "Tracing.start"
fromJSON = const . A.Success . const ()