-
Notifications
You must be signed in to change notification settings - Fork 121
/
Copy pathMultipartUtils.swift
81 lines (70 loc) · 2.35 KB
/
MultipartUtils.swift
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
import AsyncHTTPClient
import NIO
let DASHDASH = "--"
let CRLF = "\r\n"
let boundaryChars = "abcdefghijklmnopqrstuvwxyz1234567890"
open class File {
public let name: String
public var buffer: ByteBuffer
public init(name: String, buffer: ByteBuffer) {
self.name = name
self.buffer = buffer
}
}
func randomBoundary() -> String {
var string = ""
for _ in 0..<16 {
string.append(boundaryChars.randomElement()!)
}
return string
}
func buildMultipart(
_ request: inout HTTPClientRequest,
with params: [String: Any?] = [:]
) {
func addPart(name: String, value: Any) {
bodyBuffer.writeString(DASHDASH)
bodyBuffer.writeString(boundary)
bodyBuffer.writeString(CRLF)
bodyBuffer.writeString("Content-Disposition: form-data; name=\"\(name)\"")
if let file = value as? File {
bodyBuffer.writeString("; filename=\"\(file.name)\"")
bodyBuffer.writeString(CRLF)
bodyBuffer.writeString("Content-Length: \(bodyBuffer.readableBytes)")
bodyBuffer.writeString(CRLF+CRLF)
bodyBuffer.writeBuffer(&file.buffer)
bodyBuffer.writeString(CRLF)
return
}
let string = String(describing: value)
bodyBuffer.writeString(CRLF)
bodyBuffer.writeString("Content-Length: \(string.count)")
bodyBuffer.writeString(CRLF+CRLF)
bodyBuffer.writeString(string)
bodyBuffer.writeString(CRLF)
}
let boundary = randomBoundary()
var bodyBuffer = ByteBuffer()
for (key, value) in params {
switch key {
case "file":
addPart(name: key, value: value!)
default:
if let list = value as? [Any] {
for listValue in list {
addPart(name: "\(key)[]", value: listValue)
}
continue
}
addPart(name: key, value: value!)
}
}
bodyBuffer.writeString(DASHDASH)
bodyBuffer.writeString(boundary)
bodyBuffer.writeString(DASHDASH)
bodyBuffer.writeString(CRLF)
request.headers.remove(name: "content-type")
request.headers.add(name: "Content-Length", value: bodyBuffer.readableBytes.description)
request.headers.add(name: "Content-Type", value: "multipart/form-data;boundary=\"\(boundary)\"")
request.body = .bytes(bodyBuffer)
}