diff options
| author | Gregor Kleen <gkleen@yggdrasil.li> | 2015-10-17 02:26:25 +0200 | 
|---|---|---|
| committer | Gregor Kleen <gkleen@yggdrasil.li> | 2015-10-17 02:26:25 +0200 | 
| commit | 005dc408dc09c3b479398ebe3e92efa2cd54846e (patch) | |
| tree | 23dcfe7a545885c9aa145f1ccae6d33206a87820 /servant | |
| parent | 2dcbb4482de2c352b76372b389fda20c63075295 (diff) | |
| download | thermoprint-005dc408dc09c3b479398ebe3e92efa2cd54846e.tar thermoprint-005dc408dc09c3b479398ebe3e92efa2cd54846e.tar.gz thermoprint-005dc408dc09c3b479398ebe3e92efa2cd54846e.tar.bz2 thermoprint-005dc408dc09c3b479398ebe3e92efa2cd54846e.tar.xz thermoprint-005dc408dc09c3b479398ebe3e92efa2cd54846e.zip | |
Working prototype
Diffstat (limited to 'servant')
| -rw-r--r-- | servant/api/Thermoprint/Api.hs | 28 | ||||
| -rw-r--r-- | servant/servant.cabal | 31 | ||||
| -rw-r--r-- | servant/servant.nix | 5 | ||||
| -rw-r--r-- | servant/src/Main.hs | 71 | 
4 files changed, 129 insertions, 6 deletions
| diff --git a/servant/api/Thermoprint/Api.hs b/servant/api/Thermoprint/Api.hs new file mode 100644 index 0000000..bd5744b --- /dev/null +++ b/servant/api/Thermoprint/Api.hs | |||
| @@ -0,0 +1,28 @@ | |||
| 1 | {-# LANGUAGE DataKinds, TypeOperators, DeriveGeneric #-} | ||
| 2 | |||
| 3 | module Thermoprint.Api | ||
| 4 | ( ThermoprintApi | ||
| 5 | ) where | ||
| 6 | |||
| 7 | import Thermoprint | ||
| 8 | import Data.Aeson | ||
| 9 | import Servant.API | ||
| 10 | import qualified Data.Text.Lazy as Text | ||
| 11 | import qualified Data.ByteString.Lazy.Char8 as ByteString | ||
| 12 | import Data.ByteString.Lazy.Char8 (ByteString) | ||
| 13 | import GHC.Generics | ||
| 14 | |||
| 15 | import Control.Monad | ||
| 16 | |||
| 17 | instance ToJSON ByteString where | ||
| 18 | toJSON = toJSON . Text.pack . ByteString.unpack | ||
| 19 | instance FromJSON ByteString where | ||
| 20 | parseJSON value = (ByteString.pack . Text.unpack) `liftM` parseJSON value | ||
| 21 | |||
| 22 | instance ToJSON c => ToJSON (Inline c) | ||
| 23 | instance FromJSON c => FromJSON (Inline c) | ||
| 24 | |||
| 25 | instance ToJSON c => ToJSON (Block c) | ||
| 26 | instance FromJSON c => FromJSON (Block c) | ||
| 27 | |||
| 28 | type ThermoprintApi = "print" :> Capture "printerId" Integer :> ReqBody '[JSON] (Block String) :> Post '[JSON] () | ||
| diff --git a/servant/servant.cabal b/servant/servant.cabal index b509dbc..b877196 100644 --- a/servant/servant.cabal +++ b/servant/servant.cabal | |||
| @@ -16,11 +16,36 @@ build-type: Simple | |||
| 16 | -- extra-source-files: | 16 | -- extra-source-files: | 
| 17 | cabal-version: >=1.10 | 17 | cabal-version: >=1.10 | 
| 18 | 18 | ||
| 19 | library | ||
| 20 | exposed-modules: Thermoprint.Api | ||
| 21 | hs-source-dirs: api | ||
| 22 | default-language: Haskell2010 | ||
| 23 | other-extensions: DataKinds | ||
| 24 | , TypeOperators | ||
| 25 | , DeriveGeneric | ||
| 26 | build-depends: base >=4.8 && <4.9 | ||
| 27 | , thermoprint | ||
| 28 | , aeson >=0.9.0 && <0.10 | ||
| 29 | , servant >=0.4.4 && <0.5 | ||
| 30 | , text >=1.2.1 && <4.5 | ||
| 31 | , bytestring >=0.10.6 && <0.11 | ||
| 32 | |||
| 19 | executable thermoprint | 33 | executable thermoprint | 
| 20 | main-is: Main.hs | 34 | main-is: Main.hs | 
| 35 | hs-source-dirs: src | ||
| 36 | default-language: Haskell2010 | ||
| 21 | -- other-modules: | 37 | -- other-modules: | 
| 22 | -- other-extensions: | 38 | other-extensions: RecordWildCards | 
| 39 | , OverloadedStrings | ||
| 23 | build-depends: base >=4.8 && <4.9 | 40 | build-depends: base >=4.8 && <4.9 | 
| 24 | , thermoprint | 41 | , thermoprint | 
| 25 | hs-source-dirs: src | 42 | , thermoprint-servant | 
| 26 | default-language: Haskell2010 \ No newline at end of file | 43 | , aeson >=0.9.0 && <0.10 | 
| 44 | , wai >=3.0.3 && <3.1 | ||
| 45 | , servant-server >=0.4.4 && <0.5 | ||
| 46 | , warp >=3.1.3 && <3.2 | ||
| 47 | , text >=1.2.1 && <1.3 | ||
| 48 | , bytestring >=0.10.6 && <0.11 | ||
| 49 | , either >=4.4.1 && <4.5 | ||
| 50 | , optparse-applicative >=0.11.0 && <0.12 | ||
| 51 | , transformers >=0.4.2 && <0.5 \ No newline at end of file | ||
| diff --git a/servant/servant.nix b/servant/servant.nix index 6c90a4f..a84fc77 100644 --- a/servant/servant.nix +++ b/servant/servant.nix | |||
| @@ -2,16 +2,17 @@ | |||
| 2 | , stdenv | 2 | , stdenv | 
| 3 | , base | 3 | , base | 
| 4 | , thermoprint | 4 | , thermoprint | 
| 5 | , aeson, wai, servant-server, warp, optparse-applicative | ||
| 5 | }: | 6 | }: | 
| 6 | 7 | ||
| 7 | mkDerivation { | 8 | mkDerivation { | 
| 8 | pname = "thermoprint-servant"; | 9 | pname = "thermoprint-servant"; | 
| 9 | version = "0.0.0"; | 10 | version = "0.0.0"; | 
| 10 | src = ./.; | 11 | src = ./.; | 
| 11 | isLibrary = false; | 12 | isLibrary = true; | 
| 12 | isExecutable = true; | 13 | isExecutable = true; | 
| 13 | executableHaskellDepends = [ | 14 | executableHaskellDepends = [ | 
| 14 | base thermoprint | 15 | base thermoprint aeson wai servant-server warp optparse-applicative | 
| 15 | ]; | 16 | ]; | 
| 16 | homepage = "git://git.yggdrasil.li/thermoprint"; | 17 | homepage = "git://git.yggdrasil.li/thermoprint"; | 
| 17 | description = "Server for interfacing to cheap thermoprinters"; | 18 | description = "Server for interfacing to cheap thermoprinters"; | 
| diff --git a/servant/src/Main.hs b/servant/src/Main.hs index e9e1deb..9d88559 100644 --- a/servant/src/Main.hs +++ b/servant/src/Main.hs | |||
| @@ -1,2 +1,71 @@ | |||
| 1 | {-# LANGUAGE RecordWildCards, OverloadedStrings #-} | ||
| 2 | |||
| 3 | import Thermoprint | ||
| 4 | import Thermoprint.Api | ||
| 5 | |||
| 6 | import Data.Aeson | ||
| 7 | import Network.Wai | ||
| 8 | import Network.Wai.Handler.Warp | ||
| 9 | import Servant | ||
| 10 | import qualified Data.Text.Lazy as Text | ||
| 11 | import qualified Data.ByteString.Lazy.Char8 as ByteString | ||
| 12 | import Data.ByteString.Lazy.Char8 (ByteString) | ||
| 13 | import GHC.Generics | ||
| 14 | |||
| 15 | import Control.Monad | ||
| 16 | import Control.Monad.IO.Class | ||
| 17 | import Control.Monad.Trans.Either | ||
| 18 | |||
| 19 | import Options.Applicative | ||
| 20 | |||
| 21 | import System.IO | ||
| 22 | |||
| 23 | server :: Options -> Integer -> Block String -> EitherT ServantErr IO () | ||
| 24 | server Options{..} printerNo printOut = do | ||
| 25 | printerPath <- case genericIndex printers printerNo of | ||
| 26 | Just path -> return path | ||
| 27 | Nothing -> left $ err404 { errBody = "printerId out of bounds" } | ||
| 28 | liftIO $ withFile printerPath WriteMode doPrint | ||
| 29 | where | ||
| 30 | doPrint handle = do | ||
| 31 | hSetBuffering handle NoBuffering | ||
| 32 | ByteString.hPut handle $ render' printOut | ||
| 33 | genericIndex :: Integral i => [a] -> i -> Maybe a | ||
| 34 | genericIndex (x:_) 0 = Just x | ||
| 35 | genericIndex (_:xs) n | ||
| 36 | | n > 0 = genericIndex xs (n - 1) | ||
| 37 | | otherwise = Nothing | ||
| 38 | genericIndex _ _ = Nothing | ||
| 39 | |||
| 40 | data Options = Options | ||
| 41 | { port :: Int | ||
| 42 | , printers :: [FilePath] | ||
| 43 | } | ||
| 44 | |||
| 45 | options :: Parser Options | ||
| 46 | options = Options | ||
| 47 | <$> option auto ( | ||
| 48 | long "port" | ||
| 49 | <> short 'p' | ||
| 50 | <> metavar "PORT" | ||
| 51 | <> help "The port we'll run the server on" | ||
| 52 | <> value 8080 | ||
| 53 | <> showDefault | ||
| 54 | ) | ||
| 55 | <*> some (strArgument ( | ||
| 56 | metavar "PATH [...]" | ||
| 57 | <> help "Path to one of the printers to use" | ||
| 58 | )) | ||
| 59 | |||
| 60 | thermoprintApi :: Proxy ThermoprintApi | ||
| 61 | thermoprintApi = Proxy | ||
| 62 | |||
| 1 | main :: IO () | 63 | main :: IO () | 
| 2 | main = undefined | 64 | main = do | 
| 65 | execParser opts >>= main' | ||
| 66 | where | ||
| 67 | opts = info (helper <*> options) ( | ||
| 68 | fullDesc | ||
| 69 | <> header "thermoprint-servant - A REST server for interacting with a cheap thermoprinter" | ||
| 70 | ) | ||
| 71 | main' args@(Options{..}) = run port $ serve thermoprintApi (server args) | ||
