dataframe-th 2.3.0.0 → 2.3.1.0
raw patch · 3 files changed
+79/−4 lines, 3 filesdep −dataframe-operationsdep ~dataframe-core
Dependencies removed: dataframe-operations
Dependency ranges changed: dataframe-core
Files
- dataframe-th.cabal +3/−3
- src/DataFrame/TH/Identifier.hs +75/−0
- src/DataFrame/TH/Records.hs +1/−1
dataframe-th.cabal view
@@ -1,6 +1,6 @@ cabal-version: 3.4 name: dataframe-th-version: 2.3.0.0+version: 2.3.1.0 synopsis: Record-based Template Haskell splices for the dataframe ecosystem. description: The IO-agnostic part of the @dataframe@ TH machinery — splices that@@ -27,6 +27,7 @@ library import: warnings exposed-modules:+ DataFrame.TH.Identifier DataFrame.TH.Records DataFrame.Typed.TH.Records -- Internal record→schema TH; sealed (superseded publicly by@@ -34,8 +35,7 @@ other-modules: DataFrame.Internal.Schema.TH build-depends: base >= 4 && < 5, containers >= 0.6.7 && < 0.10,- dataframe-core >= 2.6 && < 2.7,- dataframe-operations >= 2.6 && < 2.7,+ dataframe-core >= 2.7 && < 2.8, dataframe-parsing >= 2.2 && < 2.3, template-haskell >= 2.0 && < 3, text >= 2.1 && < 3,
+ src/DataFrame/TH/Identifier.hs view
@@ -0,0 +1,75 @@+{-# LANGUAGE OverloadedStrings #-}++-- | Turning column names into valid Haskell identifiers for generated code.+module DataFrame.TH.Identifier (+ sanitize,+ isHaskellIdentifier,+ isReservedId,+ isVarId,+) where++import qualified Data.Char as Char+import qualified Data.Text as T++-- | Haskell Report 2.4 reserved words.+isReservedId :: T.Text -> Bool+isReservedId t = case t of+ "case" -> True+ "class" -> True+ "data" -> True+ "default" -> True+ "deriving" -> True+ "do" -> True+ "else" -> True+ "foreign" -> True+ "if" -> True+ "import" -> True+ "in" -> True+ "infix" -> True+ "infixl" -> True+ "infixr" -> True+ "instance" -> True+ "let" -> True+ "module" -> True+ "newtype" -> True+ "of" -> True+ "then" -> True+ "type" -> True+ "where" -> True+ _ -> False++isVarId :: T.Text -> Bool+isVarId t = case T.uncons t of+ -- '_' is skipped on purpose so "Name" and "_Name_" cannot collide.+ Just (c, _) -> Char.isLower c && Char.isAlpha c+ Nothing -> False++isHaskellIdentifier :: T.Text -> Bool+isHaskellIdentifier t = Prelude.not (isVarId t) || isReservedId t++sanitize :: T.Text -> T.Text+sanitize t+ | isValid = t+ | isHaskellIdentifier t' = "_" <> t' <> "_"+ | otherwise = t'+ where+ isValid =+ Prelude.not (isHaskellIdentifier t)+ && isVarId t+ && T.all Char.isAlphaNum t+ t' = T.map replaceInvalidCharacters . T.filter (Prelude.not . parentheses) $ t+ replaceInvalidCharacters c+ | Char.isUpper c = Char.toLower c+ | Char.isSpace c = '_'+ | Char.isPunctuation c = '_' -- '-' will also become a '_'+ | Char.isSymbol c = '_'+ | Char.isAlphaNum c = c -- Blanket condition+ | otherwise = '_' -- If we're unsure we'll default to an underscore+ parentheses c = case c of+ '(' -> True+ ')' -> True+ '{' -> True+ '}' -> True+ '[' -> True+ ']' -> True+ _ -> False
src/DataFrame/TH/Records.hs view
@@ -41,7 +41,6 @@ import qualified Language.Haskell.TH.Syntax as TH import DataFrame.Expression.Operators (col)-import DataFrame.Functions (sanitize) import DataFrame.Internal.Column (columnTypeString) import DataFrame.Internal.DataFrame ( DataFrame (..),@@ -50,6 +49,7 @@ import DataFrame.Internal.Expression (Expr) import DataFrame.Internal.Schema.TH (schemaTypeE) import DataFrame.Schema (Schema, makeSchema)+import DataFrame.TH.Identifier (sanitize) import Prelude as P knownTypeNames :: M.Map String Name