language-docker-1.0.0: src/Language/Docker/Normalize.hs
{-# LANGUAGE FlexibleContexts #-}
module Language.Docker.Normalize
( normalizeEscapedLines
) where
import Data.List (intercalate)
import Data.List.Split (splitOn)
escapePlaceHolder :: String
escapePlaceHolder = "\\\\"
escapeSeq :: String
escapeSeq = "\\\n"
replace :: Eq a => [a] -> [a] -> [a] -> [a]
replace old new = intercalate new . splitOn old
count :: Eq a => [a] -> [a] -> Int
count s x = length (splitOn x s) - 1
trimLines :: String -> String
trimLines s = unlines $ map strip $ lines s
where
strip = lstrip . rstrip
lstrip = dropWhile (`elem` (" \t" :: String))
rstrip = reverse . lstrip . reverse
replaceEscapeSigns :: String -> String
replaceEscapeSigns = replace escapeSeq escapePlaceHolder
removeEscapePlaceholder :: String -> String
removeEscapePlaceholder = replace escapePlaceHolder " "
compensateLinebreaks :: String -> String
compensateLinebreaks s = concatMap compensate $ lines s
where
compensate line = line ++ "\n" ++ genLinebreaks line
genLinebreaks line = concat $ replicate (count line escapePlaceHolder) "\n"
-- | Remove new line escapes and join escaped lines together on one line
-- to simplify parsing later on. Escapes are replaced with line breaks
-- to not alter the line numbers.
normalizeEscapedLines :: String -> String
normalizeEscapedLines s =
removeEscapePlaceholder $ compensateLinebreaks $ replaceEscapeSigns $ trimLines s