Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- {-# LANGUAGE OverloadedStrings #-}
- module Netcrawl.ArpDiff
- ( doArpDiff
- ) where
- import Colonnade (Colonnade, Headed)
- import qualified Colonnade as C
- import qualified Data.Aeson as AE
- import qualified Data.ByteString.Char8 as CS
- import Data.ByteString.Lazy.Char8 (ByteString)
- import qualified Data.ByteString.Lazy.Char8 as CL
- import qualified Data.Map as M
- import qualified Data.Map.Merge.Strict as MS
- import Data.Map.Strict (Map)
- import Data.Maybe (fromMaybe)
- import Data.Monoid (mconcat, (<>))
- import Data.Profunctor (lmap)
- import Data.Text (Text)
- import qualified Data.Text as T
- import qualified Data.Text.Lazy.Builder as LB
- import qualified Data.Text.Lazy.Builder as TB
- import qualified Data.Text.Lazy.IO as LTIO
- import qualified Net.Mac as Mac
- import Netcrawl.Prelude
- import Netcrawl.Types (ArpDelta (..), DeltaMac (..),
- Device (..), InterfaceIndex (..))
- import Siphon (Siphon)
- import qualified Siphon as S
- import qualified Net.IPv4 as IP
- arpDiff ::
- Map IPv4 Mac
- -> Map IPv4 Mac
- -> Map IPv4 ArpDelta
- arpDiff m1 m2 =
- MS.merge
- (MS.mapMissing (\_ x -> ArpOld x)) -- preserve keys found in m1 but not m2
- (MS.mapMissing (\_ x -> ArpNew x)) -- preserve keys found in m2 but not m1
- (MS.zipWithMaybeMatched (\_ v1 v2 -> if v1 == v2 then Nothing else Just (ArpDelta (DeltaMac v1 v2)))) -- Apply f when keys in both m1 and m2
- m1
- m2
- decodeDevice :: ByteString -> Maybe Device
- decodeDevice b = case AE.decode b of
- Nothing -> Nothing
- Just x -> Just x
- decodeArp :: ByteString -> Maybe (Map IPv4 Mac)
- decodeArp b = case decodeDevice b of
- Nothing -> Nothing
- Just x -> Just (deviceArp x)
- data ArpThing = ArpThing
- { ip :: IPv4
- , old :: Maybe Mac
- , new :: Maybe Mac }
- deltaToThing :: IPv4 -> ArpDelta -> ArpThing
- deltaToThing i (ArpDelta (DeltaMac m1 m2)) = ArpThing i (Just m1) (Just m2)
- deltaToThing i (ArpOld m1) = ArpThing i (Just m1) Nothing
- deltaToThing i (ArpNew m2) = ArpThing i Nothing (Just m2)
- data Newness = Old | New
- thingToText :: Newness -> ArpThing -> Text
- thingToText Old a = case old a of
- Nothing -> ""
- Just x -> Mac.encode x
- thingToText New a = case new a of
- Nothing -> ""
- Just x -> Mac.encode x
- doArpDiff :: FilePath -> FilePath -> IO ()
- doArpDiff x y = do
- xContents <- CL.readFile x
- yContents <- CL.readFile y
- let arp1 = decodeArp xContents
- arp2 = decodeArp yContents
- diff = arpDiff (fromMaybe M.empty arp1) (fromMaybe M.empty arp2)
- diffList = M.toList diff
- print diffList
- --putStrLn "\n"
- --CL.putStrLn (CL.append (CL.pack "ip,old,new\n") (CSV.encode diffList'))
- -- replace csv encoder with siphon to unhell yourself
- let colArp :: Colonnade Headed ArpThing Text
- colArp = mconcat
- [ C.headed "IP" (IP.encode . ip )
- , C.headed "Old" (thingToText Old)
- , C.headed "New" (thingToText New)
- ]
- --LTIO.putStr (TB.toLazyText (S.encodeCsv colArp diffList))
- print "meow"
Add Comment
Please, Sign In to add comment