Skip to content

Commit

Permalink
Support FileIO without Foundation (#284)
Browse files Browse the repository at this point in the history
* Support FileIO without Foundation

* Split up FilesTests into FileIOTests and FileMiddlewareTests
  • Loading branch information
Joannis authored Nov 21, 2023
1 parent feaa75b commit c375cbb
Show file tree
Hide file tree
Showing 4 changed files with 94 additions and 72 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,6 @@
//
//===----------------------------------------------------------------------===//

import Hummingbird

/// Associates cache control values with filename
public struct HBCacheControl: Sendable {
public enum Value: CustomStringConvertible, Sendable {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@
//
//===----------------------------------------------------------------------===//

import Hummingbird
import HummingbirdCore
import Logging
import NIOCore
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
//
// This source file is part of the Hummingbird server framework project
//
// Copyright (c) 2021-2021 the Hummingbird authors
// Copyright (c) 2021-2023 the Hummingbird authors
// Licensed under Apache License v2.0
//
// See LICENSE.txt for license information
Expand Down Expand Up @@ -53,28 +53,6 @@ class HummingbirdFilesTests: XCTestCase {
}
}

func testReadFileIO() async throws {
let router = HBRouterBuilder(context: HBTestRouterContext.self)
router.get("test.jpg") { _, context -> HBResponse in
let fileIO = HBFileIO(threadPool: context.threadPool)
let body = try await fileIO.loadFile(path: "test.jpg", context: context, logger: context.logger)
return .init(status: .ok, headers: [:], body: body)
}
let buffer = self.randomBuffer(size: 320_003)
let data = Data(buffer: buffer)
let fileURL = URL(fileURLWithPath: "test.jpg")
XCTAssertNoThrow(try data.write(to: fileURL))
defer { XCTAssertNoThrow(try FileManager.default.removeItem(at: fileURL)) }

let app = HBApplication(responder: router.buildResponder())

try await app.test(.router) { client in
try await client.XCTExecute(uri: "/test.jpg", method: .GET) { response in
XCTAssertEqual(response.body, buffer)
}
}
}

func testReadLargeFile() async throws {
let router = HBRouterBuilder(context: HBTestRouterContext.self)
router.middlewares.add(HBFileMiddleware("."))
Expand Down Expand Up @@ -322,50 +300,4 @@ class HummingbirdFilesTests: XCTestCase {
}
}
}

func testWrite() async throws {
let filename = "testWrite.txt"
let router = HBRouterBuilder(context: HBTestRouterContext.self)
router.put("store") { request, context -> HTTPResponseStatus in
let fileIO = HBFileIO(threadPool: context.threadPool)
try await fileIO.writeFile(contents: request.body, path: filename, context: context, logger: context.logger)
return .ok
}
let app = HBApplication(responder: router.buildResponder())

try await app.test(.router) { client in
let buffer = ByteBufferAllocator().buffer(string: "This is a test")
try await client.XCTExecute(uri: "/store", method: .PUT, body: buffer) { response in
XCTAssertEqual(response.status, .ok)
}
}

let fileURL = URL(fileURLWithPath: filename)
let data = try Data(contentsOf: fileURL)
defer { XCTAssertNoThrow(try FileManager.default.removeItem(at: fileURL)) }
XCTAssertEqual(String(decoding: data, as: Unicode.UTF8.self), "This is a test")
}

func testWriteLargeFile() async throws {
let filename = "testWriteLargeFile.txt"
let router = HBRouterBuilder(context: HBBasicRequestContext.self)
router.put("store", options: .streamBody) { request, context -> HTTPResponseStatus in
let fileIO = HBFileIO(threadPool: context.threadPool)
try await fileIO.writeFile(contents: request.body, path: filename, context: context, logger: context.logger)
return .ok
}
let app = HBApplication(responder: router.buildResponder())

try await app.test(.live) { client in
let buffer = self.randomBuffer(size: 400_000)
try await client.XCTExecute(uri: "/store", method: .PUT, body: buffer) { response in
XCTAssertEqual(response.status, .ok)
}

let fileURL = URL(fileURLWithPath: filename)
let data = try Data(contentsOf: fileURL)
defer { XCTAssertNoThrow(try FileManager.default.removeItem(at: fileURL)) }
XCTAssertEqual(Data(buffer: buffer), data)
}
}
}
93 changes: 93 additions & 0 deletions Tests/HummingbirdTests/FileIOTests.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
//===----------------------------------------------------------------------===//
//
// This source file is part of the Hummingbird server framework project
//
// Copyright (c) 2023 the Hummingbird authors
// Licensed under Apache License v2.0
//
// See LICENSE.txt for license information
// See hummingbird/CONTRIBUTORS.txt for the list of Hummingbird authors
//
// SPDX-License-Identifier: Apache-2.0
//
//===----------------------------------------------------------------------===//

import Hummingbird
import HummingbirdXCT
import XCTest

class FileIOTests: XCTestCase {
func randomBuffer(size: Int) -> ByteBuffer {
var data = [UInt8](repeating: 0, count: size)
data = data.map { _ in UInt8.random(in: 0...255) }
return ByteBufferAllocator().buffer(bytes: data)
}

func testReadFileIO() async throws {
let router = HBRouterBuilder(context: HBTestRouterContext.self)
router.get("test.jpg") { _, context -> HBResponse in
let fileIO = HBFileIO(threadPool: context.threadPool)
let body = try await fileIO.loadFile(path: "test.jpg", context: context, logger: context.logger)
return .init(status: .ok, headers: [:], body: body)
}
let buffer = self.randomBuffer(size: 320_003)
let data = Data(buffer: buffer)
let fileURL = URL(fileURLWithPath: "test.jpg")
XCTAssertNoThrow(try data.write(to: fileURL))
defer { XCTAssertNoThrow(try FileManager.default.removeItem(at: fileURL)) }

let app = HBApplication(responder: router.buildResponder())

try await app.test(.router) { client in
try await client.XCTExecute(uri: "/test.jpg", method: .GET) { response in
XCTAssertEqual(response.body, buffer)
}
}
}

func testWrite() async throws {
let filename = "testWrite.txt"
let router = HBRouterBuilder(context: HBTestRouterContext.self)
router.put("store") { request, context -> HTTPResponseStatus in
let fileIO = HBFileIO(threadPool: context.threadPool)
try await fileIO.writeFile(contents: request.body, path: filename, context: context, logger: context.logger)
return .ok
}
let app = HBApplication(responder: router.buildResponder())

try await app.test(.router) { client in
let buffer = ByteBufferAllocator().buffer(string: "This is a test")
try await client.XCTExecute(uri: "/store", method: .PUT, body: buffer) { response in
XCTAssertEqual(response.status, .ok)
}
}

let fileURL = URL(fileURLWithPath: filename)
let data = try Data(contentsOf: fileURL)
defer { XCTAssertNoThrow(try FileManager.default.removeItem(at: fileURL)) }
XCTAssertEqual(String(decoding: data, as: Unicode.UTF8.self), "This is a test")
}

func testWriteLargeFile() async throws {
let filename = "testWriteLargeFile.txt"
let router = HBRouterBuilder(context: HBTestRouterContext.self)
router.put("store", options: .streamBody) { request, context -> HTTPResponseStatus in
let fileIO = HBFileIO(threadPool: context.threadPool)
try await fileIO.writeFile(contents: request.body, path: filename, context: context, logger: context.logger)
return .ok
}
let app = HBApplication(responder: router.buildResponder())

try await app.test(.live) { client in
let buffer = self.randomBuffer(size: 400_000)
try await client.XCTExecute(uri: "/store", method: .PUT, body: buffer) { response in
XCTAssertEqual(response.status, .ok)
}

let fileURL = URL(fileURLWithPath: filename)
let data = try Data(contentsOf: fileURL)
defer { XCTAssertNoThrow(try FileManager.default.removeItem(at: fileURL)) }
XCTAssertEqual(Data(buffer: buffer), data)
}
}
}

0 comments on commit c375cbb

Please sign in to comment.