This commit is contained in:
Orion Kindel 2024-12-01 17:13:45 -06:00
parent fcf5709823
commit c5cc100c29
Signed by untrusted user who does not match committer: orion
GPG Key ID: 6D4165AE4C928719
9 changed files with 169 additions and 43 deletions

10
.tidyrc.json Normal file
View File

@ -0,0 +1,10 @@
{
"importSort": "source",
"importWrap": "auto",
"indent": 2,
"operatorsFile": ".tidyrc.operators",
"ribbon": 1,
"typeArrowPlacement": "last",
"unicode": "never",
"width": 80
}

16
.tidyrc.operators Normal file
View File

@ -0,0 +1,16 @@
purs-tidy
Unexpected argument:
generate-oprators
A tidy-upper for PureScript source code.
--help,-h Show this help message.
--version,-v Shows the current version.
check Check source files are formatted.
format Format input over stdin.
format-in-place Format source files in place.
generate-config Writes a .tidyrc file to the current working directory based
on the command line options given.
generate-operators Generate an operator precedence table for better operator formatting.
Best used with `spago sources`. Prints to stdout.

View File

@ -14,22 +14,22 @@ package:
- ordered-collections
- refs
- typelevel-prelude
- aff: ">=8.0.0 <9.0.0"
- argonaut-codecs: ">=9.1.0 <10.0.0"
- argonaut-core: ">=7.0.0 <8.0.0"
- console: ">=6.1.0 <7.0.0"
- effect: ">=4.0.0 <5.0.0"
- ezfetch: ">=1.1.0 <2.0.0"
- maybe: ">=6.0.0 <7.0.0"
- node-net: ">=5.1.0 <6.0.0"
- node-streams: ">=9.0.0 <10.0.0"
- nullable: ">=6.0.0 <7.0.0"
- prelude: ">=6.0.1 <7.0.0"
- strings: ">=6.0.1 <7.0.0"
- transformers: ">=6.1.0 <7.0.0"
- tuples: ">=7.0.0 <8.0.0"
- url-immutable: ">=1.0.0 <2.0.0"
- web-streams: ">=4.0.0 <5.0.0"
- aff: '>=8.0.0 <9.0.0'
- argonaut-codecs: '>=9.1.0 <10.0.0'
- argonaut-core: '>=7.0.0 <8.0.0'
- console: '>=6.1.0 <7.0.0'
- effect: '>=4.0.0 <5.0.0'
- ezfetch: '>=1.1.0 <2.0.0'
- maybe: '>=6.0.0 <7.0.0'
- node-net: '>=5.1.0 <6.0.0'
- node-streams: '>=9.0.0 <10.0.0'
- nullable: '>=6.0.0 <7.0.0'
- prelude: '>=6.0.1 <7.0.0'
- strings: '>=6.0.1 <7.0.0'
- transformers: '>=6.1.0 <7.0.0'
- tuples: '>=7.0.0 <8.0.0'
- url-immutable: '>=1.0.0 <2.0.0'
- web-streams: '>=4.0.0 <5.0.0'
test:
main: Test.Main
dependencies:

View File

@ -1,4 +1,10 @@
module Axon.Request.Parts.Class (class RequestParts, extractRequestParts, module Parts.Method, module Parts.Body, module Path.Parts) where
module Axon.Request.Parts.Class
( class RequestParts
, extractRequestParts
, module Parts.Method
, module Parts.Body
, module Path.Parts
) where
import Prelude
@ -8,10 +14,34 @@ import Axon.Request.Method (Method)
import Axon.Request.Method as Method
import Axon.Request.Parts.Body (Json(..), Stream(..))
import Axon.Request.Parts.Body (Json(..), Stream(..)) as Parts.Body
import Axon.Request.Parts.Method (Connect, Delete, Get, Options, Patch, Post, Put, Trace)
import Axon.Request.Parts.Method (Get(..), Post(..), Put(..), Patch(..), Delete(..), Trace(..), Options(..), Connect(..)) as Parts.Method
import Axon.Request.Parts.Method
( Connect
, Delete
, Get
, Options
, Patch
, Post
, Put
, Trace
)
import Axon.Request.Parts.Method
( Get(..)
, Post(..)
, Put(..)
, Patch(..)
, Delete(..)
, Trace(..)
, Options(..)
, Connect(..)
) as Parts.Method
import Axon.Request.Parts.Path (Path(..)) as Path.Parts
import Axon.Request.Parts.Path (class DiscardTupledUnits, class PathParts, Path(..), discardTupledUnits, extractPathParts)
import Axon.Request.Parts.Path
( class DiscardTupledUnits
, class PathParts
, Path(..)
, discardTupledUnits
, extractPathParts
)
import Axon.Response (Response)
import Axon.Response as Response
import Control.Alternative (guard)
@ -30,7 +60,13 @@ import Effect.Aff (Aff)
import Effect.Class (liftEffect)
import Node.Buffer (Buffer)
extractMethod :: forall @t a. RequestParts a => Newtype t a => Method -> Request -> Aff (Either Response (Maybe t))
extractMethod ::
forall @t a.
RequestParts a =>
Newtype t a =>
Method ->
Request ->
Aff (Either Response (Maybe t))
extractMethod method r =
if Request.method r == method then
extractRequestParts @a r

View File

@ -38,7 +38,11 @@ instance (DiscardTupledUnits a b) => DiscardTupledUnits (Unit /\ a) b where
discardTupledUnits (_ /\ a) = discardTupledUnits a
else instance (DiscardTupledUnits a b) => DiscardTupledUnits (a /\ Unit) b where
discardTupledUnits (a /\ _) = discardTupledUnits a
else instance (DiscardTupledUnits aa ab, DiscardTupledUnits ba bb) => DiscardTupledUnits (aa /\ ba) (ab /\ bb) where
else instance
( DiscardTupledUnits aa ab
, DiscardTupledUnits ba bb
) =>
DiscardTupledUnits (aa /\ ba) (ab /\ bb) where
discardTupledUnits (a /\ b) = discardTupledUnits a /\ discardTupledUnits b
else instance DiscardTupledUnits a a where
discardTupledUnits = identity

View File

@ -1,4 +1,24 @@
module Axon.Request (Request, Body(..), BodyReadableError(..), BodyStringError(..), BodyJSONError(..), BodyBufferError(..), bodyReadable, bodyString, bodyJSON, bodyBuffer, headers, method, address, url, contentType, accept, contentLength, lookupHeader, make) where
module Axon.Request
( Request
, Body(..)
, BodyReadableError(..)
, BodyStringError(..)
, BodyJSONError(..)
, BodyBufferError(..)
, bodyReadable
, bodyString
, bodyJSON
, bodyBuffer
, headers
, method
, address
, url
, contentType
, accept
, contentLength
, lookupHeader
, make
) where
import Prelude
@ -54,7 +74,8 @@ data BodyBufferError
derive instance Generic BodyBufferError _
instance Eq BodyBufferError where
eq (BodyBufferErrorReadable a) (BodyBufferErrorReadable b) = a == b
eq (BodyBufferErrorReading a) (BodyBufferErrorReading b) = Error.message a == Error.message b
eq (BodyBufferErrorReading a) (BodyBufferErrorReading b) = Error.message a ==
Error.message b
eq _ _ = false
instance Show BodyBufferError where
@ -95,17 +116,26 @@ data Request =
, bodyRef :: Effect.Ref Body
}
make
:: { headers :: Map String String
, address :: Either (SocketAddress IPv4) (SocketAddress IPv6)
, url :: URL
, method :: Method
, body :: Body
}
-> Effect Request
make ::
{ headers :: Map String String
, address :: Either (SocketAddress IPv4) (SocketAddress IPv6)
, url :: URL
, method :: Method
, body :: Body
} ->
Effect Request
make a = do
bodyRef <- Ref.new a.body
pure $ Request { bodyRef: bodyRef, headers: foldlWithIndex (\k m v -> Map.insert (String.Lower.fromString k) v m) Map.empty a.headers, address: a.address, url: a.url, method: a.method }
pure $ Request
{ bodyRef: bodyRef
, headers: foldlWithIndex
(\k m v -> Map.insert (String.Lower.fromString k) v m)
Map.empty
a.headers
, address: a.address
, url: a.url
, method: a.method
}
headers :: Request -> Map StringLower String
headers (Request a) = a.headers
@ -131,7 +161,8 @@ address (Request a) = a.address
url :: Request -> URL
url (Request a) = a.url
bodyReadable :: Request -> Effect (Either BodyReadableError (Stream.Readable ()))
bodyReadable ::
Request -> Effect (Either BodyReadableError (Stream.Readable ()))
bodyReadable (Request { bodyRef }) = runExceptT do
body <- liftEffect $ Ref.read bodyRef
case body of
@ -141,7 +172,9 @@ bodyReadable (Request { bodyRef }) = runExceptT do
Ref.write BodyReadableConsumed bodyRef $> r # lift
BodyCached buf -> Stream.readableFromBuffer buf # lift
BodyCachedString str -> Stream.readableFromString str UTF8 # lift
BodyCachedJSON json -> json # JSON.stringify # flip Buffer.fromString UTF8 >>= Stream.readableFromBuffer # lift
BodyCachedJSON json -> json # JSON.stringify # flip Buffer.fromString UTF8
>>= Stream.readableFromBuffer
# lift
bodyBuffer :: Request -> Aff (Either BodyBufferError Buffer)
bodyBuffer r@(Request { bodyRef }) =
@ -164,7 +197,8 @@ bodyBuffer r@(Request { bodyRef }) =
case body of
BodyCached buf -> pure buf
BodyCachedString str -> Buffer.fromString str UTF8 # liftEffect
BodyCachedJSON json -> Buffer.fromString (JSON.stringify json) UTF8 # liftEffect
BodyCachedJSON json -> Buffer.fromString (JSON.stringify json) UTF8 #
liftEffect
_ -> do
buf <- stream >>= readAll
Ref.write (BodyCached buf) bodyRef $> buf # liftEffect

View File

@ -1,4 +1,16 @@
module Axon.Response (Response(..), response, body, status, headers, withHeader, withBody, withStatus, fromStatus, ok, module Body) where
module Axon.Response
( Response(..)
, response
, body
, status
, headers
, withHeader
, withBody
, withStatus
, fromStatus
, ok
, module Body
) where
import Prelude
@ -12,14 +24,21 @@ import Data.Show.Generic (genericShow)
import Data.String.Lower (StringLower)
import Data.String.Lower as String.Lower
data Response = Response { body :: Body, headers :: Map StringLower String, status :: Int }
data Response = Response
{ body :: Body, headers :: Map StringLower String, status :: Int }
derive instance Generic Response _
instance Show Response where
show = genericShow
response :: Int -> Body -> Map String String -> Response
response s b h = Response { status: s, body: b, headers: h # foldlWithIndex (\k m v -> Map.insert (String.Lower.fromString k) v m) Map.empty }
response s b h = Response
{ status: s
, body: b
, headers: h # foldlWithIndex
(\k m v -> Map.insert (String.Lower.fromString k) v m)
Map.empty
}
status :: Response -> Int
status (Response a) = a.status
@ -31,7 +50,8 @@ headers :: Response -> Map StringLower String
headers (Response a) = a.headers
withHeader :: String -> String -> Response -> Response
withHeader k v (Response a) = Response $ a { headers = Map.insert (String.Lower.fromString k) v a.headers }
withHeader k v (Response a) = Response $ a
{ headers = Map.insert (String.Lower.fromString k) v a.headers }
withStatus :: Int -> Response -> Response
withStatus s (Response a) = Response $ a { status = s }

View File

@ -4,4 +4,7 @@ import Data.Tuple.Nested (type (/\))
import Effect (Effect)
foreign import data WebHeaders :: Type
foreign import headerEntries :: { tuple :: forall a b. a -> b -> a /\ b } -> WebHeaders -> Effect (Array (String /\ String))
foreign import headerEntries ::
{ tuple :: forall a b. a -> b -> a /\ b } ->
WebHeaders ->
Effect (Array (String /\ String))

View File

@ -9,11 +9,14 @@ import Web.Streams.ReadableStream (ReadableStream)
foreign import data WebRequest :: Type
foreign import body :: WebRequest -> Effect (Nullable (ReadableStream Uint8Array))
foreign import body ::
WebRequest -> Effect (Nullable (ReadableStream Uint8Array))
foreign import bodyUsed :: WebRequest -> Effect Boolean
foreign import method :: WebRequest -> Effect String
foreign import url :: WebRequest -> Effect String
foreign import headers :: WebRequest -> Effect WebHeaders
foreign import readableFromWeb :: ReadableStream Uint8Array -> Effect (Stream.Readable ())
foreign import readableFromWeb ::
ReadableStream Uint8Array -> Effect (Stream.Readable ())