@@ -5,7 +5,7 @@ import Control.Monad.Except (ExceptT, runExceptT)
55import Control.Monad.Reader (ReaderT, runReaderT)
66import Data.Aeson (FromJSON, ToJSON, decode, encode,
77 genericParseJSON, genericToJSON, object,
8− parseJSON, toJSON, (.:), (.=))
8+ parseJSON, toJSON, (.:), (.:?), (.=))
99import qualified Data.Aeson as JSON
1010import Data.Aeson.Types (defaultOptions, fieldLabelModifier)
1111import qualified Data.ByteString.Lazy as BL
@@ -97,8 +97,64 @@ instance FromJSON DockerVersion where
9797 parseJSON = genericParseJSON defaultOptions {
9898 fieldLabelModifier = (\(x:xs) -> toUpper x : xs)}
9999
100+
101+data ContainerPortInfo = ContainerPortInfo {
102+ ipAddressInfo :: Maybe Text
103+ , privatePortInfo :: Port
104+ , publicPortInfo :: Maybe Port
105+ , portTypeInfo :: Maybe PortType
106+ } deriving (Eq, Show)
107+
108+instance FromJSON ContainerPortInfo where
109+ parseJSON (JSON.Object v) =
110+ ContainerPortInfo <$> (v .:? "IP")
111+ <*> (v .: "PrivatePort")
112+ <*> (v .:? "PublicPort")
113+ <*> (v .:? "Type")
114+
115+-- data NetworkOptions = NetworkOptions {
116+-- ipamConfig :: Maybe Text
117+-- , links :: Maybe Text
118+-- , aliases :: Maybe Text
119+-- , networkId :: Text
120+-- , endpointId :: Text
121+-- , gateway :: Text
122+-- , ipAddress :: Text
123+-- , ipPrefixLen :: Text
124+-- , ipV6Gateway :: Maybe Text
125+-- , globalIPv6Address :: Maybe Text
126+-- , globalIPv6PrefixLen :: Maybe Text
127+-- , macAddress :: Text
128+-- } deriving (Eq, Show)
129+
130+-- data Network = Network (M.Map NetworkMode NetworkOptions) deriving (Eq, Show)
131+
132+-- data NetworkSettings = NetworkSettings {
133+-- bridge
134+-- , sandboxId
135+-- , hairpinMode
136+-- , linkLocalIPv6Address
137+-- , linkLocalIPv6PrefixLen
138+-- , ports
139+-- , sandboxKey
140+-- , secondaryIPAddresses
141+-- , secondaryIPv6Addresses
142+-- , endpointID
143+-- , gateway
144+-- , globalIPv6Address
145+-- , globalIPv6PrefixLen
146+-- , ipAddress
147+-- , ipPrefixLen
148+-- , ipv6Gateway
149+-- , macAddress
150+-- , networks :: [Network]
151+-- }
152+
153+-- data NetworkSettings = NetworkSettings (M.Map Text Text) deriving (Eq, Show, Generic)
154+
155+-- instance FromJSON NetworkSettings
156+
100157-- TODO: Add NetworkSettings
101−-- TODO: Add PortBindings
102158data Container = Container
103159 { containerId :: ContainerID
104160 , containerNames :: [Text]
@@ -107,9 +163,9 @@ data Container = Container
107163 , containerCommand :: Text
108164 , containerCreatedAt :: Int
109165 , containerStatus :: Text
110− -- , containerPorts :: Text
166+ , containerPorts :: [ContainerPortInfo]
111167 , containerLabels :: Labels
112− -- , containerNetworkSettings :: Text
168+ -- , containerNetworkSettings :: NetworkSettings
113169 } deriving (Show, Eq)
114170
115171instance FromJSON Container where
@@ -121,12 +177,10 @@ instance FromJSON Container where
121177 <*> (v .: "Command")
122178 <*> (v .: "Created")
123179 <*> (v .: "Status")
124− -- <*> (v .: "Ports")
180+ <*> (v .: "Ports")
125181 <*> (v .: "Labels")
126182 -- <*> (v .: "NetworkSettings")
127183
128−
129−
130184data Status = Created | Restarting | Running | Paused | Exited | Dead deriving (Eq, Show, Generic)
131185
132186instance FromJSON Status
@@ -160,7 +214,11 @@ instance FromJSON Image where
160214 parseJSON = genericParseJSON defaultOptions {
161215 fieldLabelModifier = dropImagePrefix}
162216
163−data CreateOpts = CreateOpts
217+data CreateOpts = CreateOpts {
218+ containerConfig :: ContainerConfig
219+ , hostConfig :: HostConfig
220+ , containerResources :: ContainerResources
221+ } deriving (Eq, Show)
164222
165223-- detachKeys – Override the key sequence for detaching a container.
166224-- Format is a single character [a-Z] or ctrl-<value> where <value> is one of: a-z, @, ^, [, , or _.
@@ -224,8 +282,8 @@ data Link = Link Text (Maybe Text) deriving (Eq, Show)
224282
225283instance ToJSON Link where
226284 toJSON (Link n1 n2) = toJSON $ case n2 of
227− Nothing -> T.concat[n1, ":", n1]
228− Just n -> T.concat[n1, ":", n]
285+ Nothing -> T.concat[n1, ":", n1] -- use same name in container
286+ Just n -> T.concat[n1, ":", n] -- used specified name in container
229287
230288-- { "Type": "<driver_name>", "Config": {"key1": "val1"} }
231289data LogDriverType = JsonFile | Syslog | Journald | Gelf | AwsLogs | Splunk | LoggingDisabled deriving (Eq, Show)
@@ -237,13 +295,22 @@ data LogDriverConfig = LogDriverConfig LogDriverType (Maybe LogDriverOptions) de
237295-- TODO: Add container:<name|id> mode
238296data NetworkMode = Bridge | Host | NetworkDisabled deriving (Eq, Show)
239297
240−data PortType = TCP | UDP deriving (Eq, Show)
298+data PortType = TCP | UDP deriving (Eq, Show, Generic)
299+
300+instance ToJSON PortType where
301+ toJSON TCP = "tcp"
302+ toJSON UDP = "udp"
303+
304+instance FromJSON PortType where
305+ parseJSON val = return $ case val of
306+ "tcp" -> TCP
307+ "udp" -> UDP
241308
242309newtype NetworkInterface = NetworkInterface Text deriving (Eq, Show)
243310
244311-- { <port>/<protocol>: [{ "HostPort": "<port>" }] }
245312data PortBinding = PortBinding {
246− containerPort :: Integer
313+ containerPort :: Port
247314 , portType :: PortType
248315 , hostPort :: [HostPort]
249316 } deriving (Eq, Show)