|
2 | 2 | {-# LANGUAGE DeriveDataTypeable #-}
|
3 | 3 | {-# LANGUAGE DeriveGeneric #-}
|
4 | 4 | {-# LANGUAGE FlexibleInstances #-}
|
| 5 | +{-# LANGUAGE FunctionalDependencies #-} |
5 | 6 | {-# LANGUAGE KindSignatures #-}
|
6 | 7 | {-# LANGUAGE MultiParamTypeClasses #-}
|
7 | 8 | {-# LANGUAGE OverloadedStrings #-}
|
@@ -38,13 +39,13 @@ type StreamGet = Stream 'GET
|
38 | 39 | type StreamPost = Stream 'POST
|
39 | 40 |
|
40 | 41 | -- | Stream endpoints may be implemented as producing a @StreamGenerator@ -- a function that itself takes two emit functions -- the first to be used on the first value the stream emits, and the second to be used on all subsequent values (to allow interspersed framing strategies such as comma separation).
|
41 |
| -newtype StreamGenerator a = StreamGenerator {getStreamGenerator :: (a -> IO ()) -> (a -> IO ()) -> IO ()} |
| 42 | +newtype StreamGenerator a = StreamGenerator {getStreamGenerator :: (a -> IO ()) -> (a -> IO ()) -> IO ()} |
42 | 43 |
|
43 | 44 | -- | ToStreamGenerator is intended to be implemented for types such as Conduit, Pipe, etc. By implementing this class, all such streaming abstractions can be used directly as endpoints.
|
44 |
| -class ToStreamGenerator f a where |
45 |
| - toStreamGenerator :: f a -> StreamGenerator a |
| 45 | +class ToStreamGenerator a b | a -> b where |
| 46 | + toStreamGenerator :: a -> StreamGenerator b |
46 | 47 |
|
47 |
| -instance ToStreamGenerator StreamGenerator a |
| 48 | +instance ToStreamGenerator (StreamGenerator a) a |
48 | 49 | where toStreamGenerator x = x
|
49 | 50 |
|
50 | 51 | -- | Clients reading from streaming endpoints can be implemented as producing a @ResultStream@ that captures the setup, takedown, and incremental logic for a read, being an IO continuation that takes a producer of Just either values or errors that terminates with a Nothing.
|
@@ -80,6 +81,18 @@ data ByteStringParser a = ByteStringParser {
|
80 | 81 | class FramingUnrender strategy a where
|
81 | 82 | unrenderFrames :: Proxy strategy -> Proxy a -> ByteStringParser (ByteStringParser (Either String ByteString))
|
82 | 83 |
|
| 84 | +-- | A framing strategy that does not do any framing at all, it just passes the input data |
| 85 | +-- This will be used most of the time with binary data, such as files |
| 86 | +data NoFraming |
| 87 | + |
| 88 | +instance FramingRender NoFraming a where |
| 89 | + header _ _ = empty |
| 90 | + boundary _ _ = BoundaryStrategyGeneral id |
| 91 | + trailer _ _ = empty |
| 92 | + |
| 93 | +instance FramingUnrender NoFraming a where |
| 94 | + unrenderFrames _ _ = ByteStringParser (Just . (go,)) (go,) |
| 95 | + where go = ByteStringParser (Just . (, empty) . Right) ((, empty) . Right) |
83 | 96 |
|
84 | 97 | -- | A simple framing strategy that has no header or termination, and inserts a newline character between each frame.
|
85 | 98 | -- This assumes that it is used with a Content-Type that encodes without newlines (e.g. JSON).
|
|
0 commit comments