Created
May 28, 2018 13:58
-
-
Save chriseidhof/d22d249e32e7d2463d9b28410df59f5a to your computer and use it in GitHub Desktop.
NIO Hello World
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import Foundation | |
import NIO | |
import NIOHTTP1 | |
// Inspired/parts copied from http://www.alwaysrightinstitute.com/microexpress-nio/ | |
final class HelloHandler: ChannelInboundHandler { | |
typealias InboundIn = HTTPServerRequestPart | |
func channelRead(ctx: ChannelHandlerContext, data: NIOAny) { | |
let reqPart = unwrapInboundIn(data) | |
switch reqPart { | |
case .head(let header): | |
let head = HTTPResponseHead(version: header.version, status: .ok) | |
let part = HTTPServerResponsePart.head(head) | |
_ = ctx.channel.write(part) | |
let responseStr = "Hello, world" | |
var buffer = ctx.channel.allocator.buffer(capacity: responseStr.utf8.count) | |
buffer.write(string: responseStr) | |
let bodyPart = HTTPServerResponsePart.body(.byteBuffer(buffer)) | |
_ = ctx.channel.write(bodyPart) | |
_ = ctx.channel.writeAndFlush(HTTPServerResponsePart.end(nil)).then { | |
ctx.channel.close() | |
} | |
case .body, .end: | |
break | |
} | |
} | |
} | |
struct MyServer { | |
let group = MultiThreadedEventLoopGroup(numThreads: System.coreCount) | |
func listen(port: Int = 8765) throws { | |
let reuseAddr = ChannelOptions.socket(SocketOptionLevel(SOL_SOCKET), | |
SO_REUSEADDR) | |
let bootstrap = ServerBootstrap(group: group) | |
.serverChannelOption(ChannelOptions.backlog, value: 256) | |
.serverChannelOption(reuseAddr, value: 1) | |
.childChannelInitializer { channel in | |
channel.pipeline.configureHTTPServerPipeline(withErrorHandling: true).then { | |
channel.pipeline.add(handler: HelloHandler()) | |
} | |
} | |
.childChannelOption(ChannelOptions.socket( | |
IPPROTO_TCP, TCP_NODELAY), value: 1) | |
.childChannelOption(reuseAddr, value: 1) | |
.childChannelOption(ChannelOptions.maxMessagesPerRead, | |
value: 1) | |
let channel = try bootstrap.bind(host: "localhost", port: port).wait() | |
try channel.closeFuture.wait() | |
} | |
} | |
let s = MyServer() | |
try s.listen() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment