-
Notifications
You must be signed in to change notification settings - Fork 0
/
Headers.scala
71 lines (54 loc) · 1.97 KB
/
Headers.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
package compose.http
import scala.io.Source
case class Headers(
raw: Map[String, Seq[String]],
) {
def get(key: String): Option[String] = raw.get(key.toLowerCase()).flatMap(_.lastOption)
def getAll(key: String): Seq[String] = raw.getOrElse(key.toLowerCase(), Seq.empty[String])
def iterator: Iterator[(String, String)] =
raw.iterator.flatMap { case (key, allValues) =>
allValues.map { v => (key, v) }
}
def remove(key: String): Headers =
Headers(raw.removed(key.toLowerCase()))
def replace(key: String, value: String): Headers =
Headers(raw.updated(key.toLowerCase(), Seq(value)))
def replace(pairs: (String, String)*): Headers =
Headers(raw ++ Headers(pairs: _*).raw)
def replace(other: Headers): Headers =
Headers(raw ++ other.raw)
def add(key: String, value: String): Headers =
Headers(raw.updated[Seq[String]](
key.toLowerCase(),
getAll(key) :+ value
))
def add(pairs: (String, String)*): Headers =
Headers((this.iterator ++ pairs).toSeq: _*)
def add(other: Headers): Headers =
Headers((this.iterator ++ other.iterator).toSeq: _*)
def render: String = iterator.map { case (key, value) =>
s"${Headers.formatKey(key)}: ${value}"
}.mkString("\r\n")
}
object Headers {
private[http] val encoding: String = "ISO-8859-1"
def apply(initial: (String, String)*): Headers = Headers(
(for {
(key, pairs) <- initial.groupBy(_._1.toLowerCase())
} yield (key -> pairs.map(_._2))).toMap
)
lazy val empty: Headers = Headers(Map.empty[String, Seq[String]])
def parse(source: Source): Headers = Headers(
source.getLines().takeWhile(!_.isEmpty).flatMap { line =>
val colonIndex = line.indexOf(":")
if (colonIndex >= 0) {
val key = line.take(colonIndex).trim
val value = line.drop(colonIndex + 1).trim
Some(key -> value)
} else {
None
}
}.toSeq: _*
)
def formatKey(key: String): String = key.split("-").map(_.capitalize).mkString("-")
}