packages feed

strelka-core (empty) → 0.1

raw patch · 8 files changed

+284/−0 lines, 8 filesdep +basedep +base-preludedep +bifunctorssetup-changed

Dependencies added: base, base-prelude, bifunctors, bytestring, hashable, mtl, semigroups, text, transformers, unordered-containers

Files

+ LICENSE view
@@ -0,0 +1,22 @@+Copyright (c) 2016, Nikita Volkov++Permission is hereby granted, free of charge, to any person+obtaining a copy of this software and associated documentation+files (the "Software"), to deal in the Software without+restriction, including without limitation the rights to use,+copy, modify, merge, publish, distribute, sublicense, and/or sell+copies of the Software, and to permit persons to whom the+Software is furnished to do so, subject to the following+conditions:++The above copyright notice and this permission notice shall be+included in all copies or substantial portions of the Software.++THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES+OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT+HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,+WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING+FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR+OTHER DEALINGS IN THE SOFTWARE.
+ Setup.hs view
@@ -0,0 +1,2 @@+import Distribution.Simple+main = defaultMain
+ library/Strelka/Core/Executor.hs view
@@ -0,0 +1,19 @@+module Strelka.Core.Executor where++import Strelka.Core.Prelude+import Strelka.Core.Model+import qualified Strelka.Core.RequestParser as A+import qualified Strelka.Core.ResponseBuilder as B+import qualified Data.Text as C+import qualified Data.Text.Encoding as D+import qualified Data.Text.Encoding.Error as E+++route :: Monad m => Request -> A.RequestParser m B.ResponseBuilder -> m (Either Text Response)+route request route =+  (liftM . liftM) (B.run . fst) (A.run route request segments)+  where+    segments =+      case request of+        Request _ x _ _ _ ->+          x
+ library/Strelka/Core/Model.hs view
@@ -0,0 +1,55 @@+module Strelka.Core.Model where++import Strelka.Core.Prelude+++data Request =+  Request !Method ![PathSegment] !(HashMap ParamName ParamValue) !(HashMap HeaderName HeaderValue) !InputStream++data Response =+  Response !Status ![Header] !OutputStream++-- |+-- HTTP Method __in lower-case__.+newtype Method =+  Method ByteString+  deriving (IsString, Show, Eq, Ord, Hashable)++newtype PathSegment =+  PathSegment Text+  deriving (IsString, Show, Eq, Ord, Hashable)++newtype ParamName =+  ParamName ByteString+  deriving (IsString, Show, Eq, Ord, Hashable)++newtype ParamValue =+  ParamValue (Maybe ByteString)+  deriving (Show, Eq, Ord, Hashable)++data Header =+  Header !HeaderName !HeaderValue++-- |+-- Header name __in lower-case__.+newtype HeaderName =+  HeaderName ByteString+  deriving (IsString, Show, Eq, Ord, Hashable)++newtype HeaderValue =+  HeaderValue ByteString+  deriving (IsString, Show, Eq, Ord, Hashable)++newtype Status =+  Status Int++-- |+-- IO action, which produces the next chunk.+-- An empty chunk signals the end of the stream.+newtype InputStream =+  InputStream (IO ByteString)++-- |+-- A function on a chunk consuming and flushing IO actions.+newtype OutputStream =+  OutputStream ((ByteString -> IO ()) -> IO () -> IO ())
+ library/Strelka/Core/Prelude.hs view
@@ -0,0 +1,62 @@+module Strelka.Core.Prelude+( +  module Exports,+  tryError,+)+where+++-- base-prelude+-------------------------+import BasePrelude as Exports hiding (First(..), Last(..), (<>))++-- transformers+-------------------------+import Control.Monad.IO.Class as Exports+import Control.Monad.Trans.Class as Exports+import Control.Monad.Trans.Cont as Exports hiding (shift, callCC)+import Control.Monad.Trans.Except as Exports (ExceptT(ExceptT), Except, except, runExcept, runExceptT, mapExcept, mapExceptT, withExcept, withExceptT)+import Control.Monad.Trans.Maybe as Exports+import Control.Monad.Trans.Reader as Exports (Reader, runReader, mapReader, withReader, ReaderT(ReaderT), runReaderT, mapReaderT, withReaderT)+import Control.Monad.Trans.State.Strict as Exports (State, runState, evalState, execState, mapState, withState, StateT(StateT), runStateT, evalStateT, execStateT, mapStateT, withStateT)+import Control.Monad.Trans.Writer.Strict as Exports (Writer, runWriter, execWriter, mapWriter, WriterT(..), execWriterT, mapWriterT)++-- mtl+-------------------------+import Control.Monad.Cont.Class as Exports+import Control.Monad.Error.Class as Exports hiding (Error(..))+import Control.Monad.Reader.Class as Exports+import Control.Monad.State.Class as Exports+import Control.Monad.Writer.Class as Exports++-- semigroups+-------------------------+import Data.Semigroup as Exports++-- bifunctors+-------------------------+import Data.Bifunctor as Exports++-- unordered-containers+-------------------------+import Data.HashMap.Strict as Exports (HashMap)++-- bytestring+-------------------------+import Data.ByteString as Exports (ByteString)++-- text+-------------------------+import Data.Text as Exports (Text)++-- hashable+-------------------------+import Data.Hashable as Exports++-- Utils+-------------------------+import qualified Data.ByteString as ByteString++tryError :: MonadError e m => m a -> m (Either e a)+tryError m =+  catchError (liftM Right m) (return . Left)
+ library/Strelka/Core/RequestParser.hs view
@@ -0,0 +1,32 @@+module Strelka.Core.RequestParser where++import Strelka.Core.Prelude+import Strelka.Core.Model+++{-|+Parser of an HTTP request.+Analyzes its meta information, consumes the path segments and the body.+-}+newtype RequestParser m a =+  RequestParser (ReaderT Request (StateT [PathSegment] (ExceptT Text m)) a)+  deriving (Functor, Applicative, Monad, Alternative, MonadPlus, MonadError Text)++instance MonadIO m => MonadIO (RequestParser m) where+  liftIO io =+    RequestParser ((lift . lift . ExceptT . liftM (either (Left . fromString . show) Right) . liftIO . trySE) io)+    where+      trySE :: IO a -> IO (Either SomeException a)+      trySE =+        Strelka.Core.Prelude.try++instance MonadTrans RequestParser where+  lift m =+    RequestParser (lift (lift (lift m)))++{-|+Execute the parser providing a request and a list of segments.+-}+run :: RequestParser m a -> Request -> [PathSegment] -> m (Either Text (a, [PathSegment]))+run (RequestParser impl) request segments =+  runExceptT (runStateT (runReaderT impl request) segments)
+ library/Strelka/Core/ResponseBuilder.hs view
@@ -0,0 +1,28 @@+module Strelka.Core.ResponseBuilder where++import Strelka.Core.Prelude+import Strelka.Core.Model+++{-|+A composable abstraction for building an HTTP response.+-}+newtype ResponseBuilder =+  ResponseBuilder (Response -> Response)++instance Monoid ResponseBuilder where+  mempty =+    ResponseBuilder id+  mappend (ResponseBuilder fn1) (ResponseBuilder fn2) =+    ResponseBuilder (fn2 . fn1)++instance Semigroup ResponseBuilder+++{-|+Execute the builder producing Response.+-}+run :: ResponseBuilder -> Response+run (ResponseBuilder fn) =+  fn (Response (Status 200) [] (OutputStream (const (const (pure ())))))+
+ strelka-core.cabal view
@@ -0,0 +1,64 @@+name:+  strelka-core+version:+  0.1+synopsis:+  Core components of "strelka"+description:+  This library is only intended for the internal usage+  by the \"strelka\" ecosystem.+  It exposes the components,+  which may be needed by both the \"strelka\" library and+  the server drivers.+homepage:+  https://github.com/nikita-volkov/strelka-core+bug-reports:+  https://github.com/nikita-volkov/strelka-core/issues +author:+  Nikita Volkov <nikita.y.volkov@mail.ru>+maintainer:+  Nikita Volkov <nikita.y.volkov@mail.ru>+copyright:+  (c) 2016, Nikita Volkov+license:+  MIT+license-file:+  LICENSE+build-type:+  Simple+cabal-version:+  >=1.10++source-repository head+  type:+    git+  location:+    git://github.com/nikita-volkov/strelka-core.git++library+  hs-source-dirs:+    library+  other-modules:+    Strelka.Core.Prelude+  exposed-modules:+    Strelka.Core.Model+    Strelka.Core.RequestParser+    Strelka.Core.ResponseBuilder+    Strelka.Core.Executor+  default-extensions:+    Arrows, BangPatterns, ConstraintKinds, DataKinds, DefaultSignatures, DeriveDataTypeable, DeriveFoldable, DeriveFunctor, DeriveGeneric, DeriveTraversable, EmptyDataDecls, FlexibleContexts, FlexibleInstances, FunctionalDependencies, GADTs, GeneralizedNewtypeDeriving, LambdaCase, LiberalTypeSynonyms, MagicHash, MultiParamTypeClasses, MultiWayIf, NoImplicitPrelude, NoMonomorphismRestriction, OverloadedStrings, PatternGuards, ParallelListComp, QuasiQuotes, RankNTypes, RecordWildCards, ScopedTypeVariables, StandaloneDeriving, TemplateHaskell, TupleSections, TypeFamilies, TypeOperators, UnboxedTuples+  default-language:+    Haskell2010+  build-depends:+    -- +    bytestring >= 0.10 && < 0.11,+    text >= 1 && < 2,+    unordered-containers >= 0.2 && < 0.3,+    hashable == 1.*,+    -- +    bifunctors == 5.*,+    semigroups >= 0.18 && < 0.19,+    mtl == 2.*,+    transformers >= 0.4 && < 0.6,+    base-prelude < 2,+    base < 5