/
ConnectionHandler.scala
141 lines (122 loc) · 3.92 KB
/
ConnectionHandler.scala
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
package acolyte.reactivemongo
import scala.util.Try
import reactivemongo.core.protocol.Response
/** Connection handler. */
sealed trait ConnectionHandler { self ⇒
/** Query handler */
def queryHandler: QueryHandler
/** Write handler */
def writeHandler: WriteHandler
/**
* Creates a copy of this connection handler,
* with given query `handler` appended.
*
* @param handler Query handler
*/
def withQueryHandler[T](handler: T)(implicit f: T ⇒ QueryHandler) =
ConnectionHandler(new QueryHandler {
def apply(cid: Int, q: Request) =
self.queryHandler(cid, q).orElse(f(handler)(cid, q))
}, writeHandler)
/**
* Creates a copy of this connection handler,
* with given write `handler` appended.
*
* @param handler Write handler
*/
def withWriteHandler[T](handler: T)(implicit f: T ⇒ WriteHandler) =
ConnectionHandler(queryHandler, new WriteHandler {
def apply(cid: Int, op: WriteOp, w: Request) =
self.writeHandler(cid, op, w).orElse(f(handler)(cid, op, w))
})
}
/** Companion object for connection handler. */
object ConnectionHandler {
/**
* Creates connection handler using given query and write handlers.
*
* @param q Query handler
* @param w Write handler
*
* {{{
* import acolyte.reactivemongo.ConnectionHandler
*
* ConnectionHandler(myQueryHandler, myWriteHandler)
* }}}
*/
def apply[A, B](q: A = QueryHandler.empty, h: B = WriteHandler.empty)(implicit f: A ⇒ QueryHandler, g: B ⇒ WriteHandler): ConnectionHandler = new ConnectionHandler {
val queryHandler = f(q)
val writeHandler = g(h)
}
/**
* Empty connection handler, not handling any query or write request.
*/
lazy val empty: ConnectionHandler = apply()
}
/** Query handler. */
sealed trait QueryHandler extends ((Int, Request) ⇒ Option[Try[Response]]) {
/**
* @param channelId ID of channel
* @param query Query to respond to
*/
override def apply(channelId: Int, query: Request): Option[Try[Response]]
}
/** Query handler companion. */
object QueryHandler {
import scala.language.implicitConversions
/**
* Creates a query handler from given function `f`.
*
* @param f Handling function, with arguments channel ID and query.
*
* {{{
* import reactivemongo.bson.BSONDocument
* import acolyte.reactivemongo.{ Request, QueryHandler }
*
* val handler1: QueryHandler = // Returns a successful empty response
* (q: Request) => QueryResponse(Seq.empty[BSONDocument])
*
* }}}
*/
implicit def SimpleQueryHandler(f: Request ⇒ PreparedResponse): QueryHandler = new QueryHandler {
def apply(chanId: Int, q: Request): Option[Try[Response]] = f(q)(chanId)
}
/**
* Empty query handler, not handling any request.
*/
lazy val empty = SimpleQueryHandler(_ ⇒ QueryResponse(None))
}
/** Write handler. */
sealed trait WriteHandler
extends ((Int, WriteOp, Request) ⇒ Option[Try[Response]]) {
/**
* @param channelId ID of channel
* @param op Write operator
* @param req Write request
*/
override def apply(channelId: Int, op: WriteOp, req: Request): Option[Try[Response]]
}
/** Write handler companion. */
object WriteHandler {
import scala.language.implicitConversions
/**
* Creates a write handler from given function `f`.
*
* @param f Handling function, with arguments channel ID and write request.
*
* {{{
* import acolyte.reactivemongo.{ Request, WriteHandler, WriteOp }
*
* val handler1: WriteHandler = // Returns a successful empty response
* (w: (WriteOp, Request)) => WriteResponse(false)
*
* }}}
*/
implicit def SimpleWriteHandler(f: (WriteOp, Request) ⇒ PreparedResponse): WriteHandler = new WriteHandler {
def apply(chanId: Int, op: WriteOp, w: Request): Option[Try[Response]] = f(op, w)(chanId)
}
/**
* Empty query handler, not handling any request.
*/
lazy val empty = SimpleWriteHandler((_, _) ⇒ WriteResponse(None))
}