Skip to content

Commit 18737c8

Browse files
committed
Tests pass again
1 parent 71ea055 commit 18737c8

File tree

3 files changed

+126
-148
lines changed

3 files changed

+126
-148
lines changed

Sources/AWSLambdaRuntimeCore/LambdaContext.swift

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ extension Lambda {
3636
/// `ByteBufferAllocator` to allocate `ByteBuffer`
3737
public let allocator: ByteBufferAllocator
3838

39-
internal init(logger: Logger, eventLoop: EventLoop, allocator: ByteBufferAllocator) {
39+
public init(logger: Logger, eventLoop: EventLoop, allocator: ByteBufferAllocator) {
4040
self.eventLoop = eventLoop
4141
self.logger = logger
4242
self.allocator = allocator
@@ -138,15 +138,15 @@ extension Lambda {
138138
self.storage.allocator
139139
}
140140

141-
internal init(requestID: String,
142-
traceID: String,
143-
invokedFunctionARN: String,
144-
deadline: DispatchWallTime,
145-
cognitoIdentity: String? = nil,
146-
clientContext: String? = nil,
147-
logger: Logger,
148-
eventLoop: EventLoop,
149-
allocator: ByteBufferAllocator) {
141+
public init(requestID: String,
142+
traceID: String,
143+
invokedFunctionARN: String,
144+
deadline: DispatchWallTime,
145+
cognitoIdentity: String? = nil,
146+
clientContext: String? = nil,
147+
logger: Logger,
148+
eventLoop: EventLoop,
149+
allocator: ByteBufferAllocator) {
150150
self.storage = _Storage(requestID: requestID,
151151
traceID: traceID,
152152
invokedFunctionARN: invokedFunctionARN,

Sources/AWSLambdaTesting/Lambda+Testing.swift

Lines changed: 28 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -18,29 +18,33 @@
1818
// For exmaple:
1919
//
2020
// func test() {
21-
// struct MyLambda: EventLoopLambdaHandler {
21+
// struct MyLambda: LambdaHandler {
2222
// typealias In = String
2323
// typealias Out = String
2424
//
25-
// func handle(context: Lambda.Context, event: String) -> EventLoopFuture<String> {
26-
// return context.eventLoop.makeSucceededFuture("echo" + event)
25+
// init(context: Lambda.InitializationContext) {}
26+
//
27+
// func handle(event: String, context: Lambda.Context) async throws -> String {
28+
// "echo" + event
2729
// }
2830
// }
2931
//
3032
// let input = UUID().uuidString
3133
// var result: String?
32-
// XCTAssertNoThrow(result = try Lambda.test(MyLambda(), with: input))
34+
// XCTAssertNoThrow(result = try Lambda.test(MyLambda.self, with: input))
3335
// XCTAssertEqual(result, "echo" + input)
3436
// }
3537

36-
#if DEBUG
37-
@testable import AWSLambdaRuntime
38-
@testable import AWSLambdaRuntimeCore
38+
#if swift(>=5.5)
39+
import AWSLambdaRuntime
40+
import AWSLambdaRuntimeCore
3941
import Dispatch
4042
import Logging
4143
import NIOCore
4244
import NIOPosix
45+
import _NIOConcurrency
4346

47+
@available(macOS 12, iOS 15, tvOS 15, watchOS 8, *)
4448
extension Lambda {
4549
public struct TestConfig {
4650
public var requestID: String
@@ -60,25 +64,37 @@ extension Lambda {
6064
}
6165
}
6266

63-
public static func test<In, Out, Handler: EventLoopLambdaHandler>(
64-
_ handler: Handler,
65-
with event: In,
67+
public static func test<Handler: LambdaHandler>(
68+
_ handlerType: Handler.Type,
69+
with event: Handler.In,
6670
using config: TestConfig = .init()
67-
) throws -> Out where Handler.In == In, Handler.Out == Out {
71+
) throws -> Handler.Out {
6872
let logger = Logger(label: "test")
6973
let eventLoopGroup = MultiThreadedEventLoopGroup(numberOfThreads: 1)
7074
defer {
7175
try! eventLoopGroup.syncShutdownGracefully()
7276
}
7377
let eventLoop = eventLoopGroup.next()
78+
79+
let promise = eventLoop.makePromise(of: Handler.self)
80+
let initContext = Lambda.InitializationContext(
81+
logger: logger,
82+
eventLoop: eventLoop,
83+
allocator: ByteBufferAllocator())
84+
7485
let context = Context(requestID: config.requestID,
7586
traceID: config.traceID,
7687
invokedFunctionARN: config.invokedFunctionARN,
7788
deadline: .now() + config.timeout,
7889
logger: logger,
7990
eventLoop: eventLoop,
8091
allocator: ByteBufferAllocator())
81-
92+
93+
promise.completeWithTask {
94+
try await Handler(context: initContext)
95+
}
96+
let handler = try promise.futureResult.wait()
97+
8298
return try eventLoop.flatSubmit {
8399
handler.handle(context: context, event: event)
84100
}.wait()

Tests/AWSLambdaTestingTests/Tests.swift

Lines changed: 88 additions & 126 deletions
Original file line numberDiff line numberDiff line change
@@ -12,136 +12,98 @@
1212
//
1313
//===----------------------------------------------------------------------===//
1414

15+
#if swift(>=5.5)
1516
import AWSLambdaRuntime
1617
import AWSLambdaTesting
1718
import NIOCore
1819
import XCTest
1920

21+
@available(macOS 12, iOS 15, tvOS 15, watchOS 8, *)
2022
class LambdaTestingTests: XCTestCase {
21-
// func testCodableClosure() {
22-
// struct Request: Codable {
23-
// let name: String
24-
// }
25-
//
26-
// struct Response: Codable {
27-
// let message: String
28-
// }
29-
//
30-
// let myLambda = { (_: Lambda.Context, request: Request, callback: (Result<Response, Error>) -> Void) in
31-
// callback(.success(Response(message: "echo" + request.name)))
32-
// }
33-
//
34-
// let request = Request(name: UUID().uuidString)
35-
// var response: Response?
36-
// XCTAssertNoThrow(response = try Lambda.test(myLambda, with: request))
37-
// XCTAssertEqual(response?.message, "echo" + request.name)
38-
// }
39-
//
40-
// func testCodableVoidClosure() {
41-
// struct Request: Codable {
42-
// let name: String
43-
// }
44-
//
45-
// let myLambda = { (_: Lambda.Context, _: Request, callback: (Result<Void, Error>) -> Void) in
46-
// callback(.success(()))
47-
// }
48-
//
49-
// let request = Request(name: UUID().uuidString)
50-
// XCTAssertNoThrow(try Lambda.test(myLambda, with: request))
51-
// }
52-
//
53-
// func testLambdaHandler() {
54-
// struct Request: Codable {
55-
// let name: String
56-
// }
57-
//
58-
// struct Response: Codable {
59-
// let message: String
60-
// }
61-
//
62-
// struct MyLambda: LambdaHandler {
63-
// typealias In = Request
64-
// typealias Out = Response
65-
//
66-
// func handle(context: Lambda.Context, event: In, callback: @escaping (Result<Out, Error>) -> Void) {
67-
// XCTAssertFalse(context.eventLoop.inEventLoop)
68-
// callback(.success(Response(message: "echo" + event.name)))
69-
// }
70-
// }
71-
//
72-
// let request = Request(name: UUID().uuidString)
73-
// var response: Response?
74-
// XCTAssertNoThrow(response = try Lambda.test(MyLambda(), with: request))
75-
// XCTAssertEqual(response?.message, "echo" + request.name)
76-
// }
77-
//
78-
// func testEventLoopLambdaHandler() {
79-
// struct MyLambda: EventLoopLambdaHandler {
80-
// typealias In = String
81-
// typealias Out = String
82-
//
83-
// func handle(context: Lambda.Context, event: String) -> EventLoopFuture<String> {
84-
// XCTAssertTrue(context.eventLoop.inEventLoop)
85-
// return context.eventLoop.makeSucceededFuture("echo" + event)
86-
// }
87-
// }
88-
//
89-
// let input = UUID().uuidString
90-
// var result: String?
91-
// XCTAssertNoThrow(result = try Lambda.test(MyLambda(), with: input))
92-
// XCTAssertEqual(result, "echo" + input)
93-
// }
94-
//
95-
// func testFailure() {
96-
// struct MyError: Error {}
97-
//
98-
// struct MyLambda: LambdaHandler {
99-
// typealias In = String
100-
// typealias Out = Void
101-
//
102-
// func handle(context: Lambda.Context, event: In, callback: @escaping (Result<Out, Error>) -> Void) {
103-
// callback(.failure(MyError()))
104-
// }
105-
// }
106-
//
107-
// XCTAssertThrowsError(try Lambda.test(MyLambda(), with: UUID().uuidString)) { error in
108-
// XCTAssert(error is MyError)
109-
// }
110-
// }
111-
//
112-
// func testAsyncLongRunning() {
113-
// var executed: Bool = false
114-
// let myLambda = { (_: Lambda.Context, _: String, callback: @escaping (Result<Void, Error>) -> Void) in
115-
// DispatchQueue.global(qos: .background).asyncAfter(deadline: .now() + 0.5) {
116-
// executed = true
117-
// callback(.success(()))
118-
// }
119-
// }
120-
//
121-
// XCTAssertNoThrow(try Lambda.test(myLambda, with: UUID().uuidString))
122-
// XCTAssertTrue(executed)
123-
// }
124-
//
125-
// func testConfigValues() {
126-
// let timeout: TimeInterval = 4
127-
// let config = Lambda.TestConfig(
128-
// requestID: UUID().uuidString,
129-
// traceID: UUID().uuidString,
130-
// invokedFunctionARN: "arn:\(UUID().uuidString)",
131-
// timeout: .seconds(4)
132-
// )
133-
//
134-
// let myLambda = { (ctx: Lambda.Context, _: String, callback: @escaping (Result<Void, Error>) -> Void) in
135-
// XCTAssertEqual(ctx.requestID, config.requestID)
136-
// XCTAssertEqual(ctx.traceID, config.traceID)
137-
// XCTAssertEqual(ctx.invokedFunctionARN, config.invokedFunctionARN)
138-
//
139-
// let secondsSinceEpoch = Double(Int64(bitPattern: ctx.deadline.rawValue)) / -1_000_000_000
140-
// XCTAssertEqual(Date(timeIntervalSince1970: secondsSinceEpoch).timeIntervalSinceNow, timeout, accuracy: 0.1)
141-
//
142-
// callback(.success(()))
143-
// }
144-
//
145-
// XCTAssertNoThrow(try Lambda.test(myLambda, with: UUID().uuidString, using: config))
146-
// }
23+
func testCodableClosure() {
24+
struct Request: Codable {
25+
let name: String
26+
}
27+
28+
struct Response: Codable {
29+
let message: String
30+
}
31+
32+
struct MyLambda: LambdaHandler {
33+
typealias In = Request
34+
typealias Out = Response
35+
36+
init(context: Lambda.InitializationContext) {}
37+
38+
func handle(event: Request, context: Lambda.Context) async throws -> Response {
39+
Response(message: "echo" + event.name)
40+
}
41+
}
42+
43+
let request = Request(name: UUID().uuidString)
44+
var response: Response?
45+
XCTAssertNoThrow(response = try Lambda.test(MyLambda.self, with: request))
46+
XCTAssertEqual(response?.message, "echo" + request.name)
47+
}
48+
49+
// DIRTY HACK: To verify the handler was actually invoked, we change a global variable.
50+
static var VoidLambdaHandlerInvokeCount: Int = 0
51+
func testCodableVoidClosure() {
52+
struct Request: Codable {
53+
let name: String
54+
}
55+
56+
struct MyLambda: LambdaHandler {
57+
typealias In = Request
58+
typealias Out = Void
59+
60+
init(context: Lambda.InitializationContext) {}
61+
62+
func handle(event: Request, context: Lambda.Context) async throws {
63+
LambdaTestingTests.VoidLambdaHandlerInvokeCount += 1
64+
}
65+
}
66+
67+
Self.VoidLambdaHandlerInvokeCount = 0
68+
let request = Request(name: UUID().uuidString)
69+
XCTAssertNoThrow(try Lambda.test(MyLambda.self, with: request))
70+
XCTAssertEqual(Self.VoidLambdaHandlerInvokeCount, 1)
71+
}
72+
73+
func testInvocationFailure() {
74+
struct MyError: Error {}
75+
76+
struct MyLambda: LambdaHandler {
77+
typealias In = String
78+
typealias Out = Void
79+
80+
init(context: Lambda.InitializationContext) {}
81+
82+
func handle(event: String, context: Lambda.Context) async throws {
83+
throw MyError()
84+
}
85+
}
86+
87+
XCTAssertThrowsError(try Lambda.test(MyLambda.self, with: UUID().uuidString)) { error in
88+
XCTAssert(error is MyError)
89+
}
90+
}
91+
92+
func testAsyncLongRunning() {
93+
struct MyLambda: LambdaHandler {
94+
typealias In = String
95+
typealias Out = String
96+
97+
init(context: Lambda.InitializationContext) {}
98+
99+
func handle(event: String, context: Lambda.Context) async throws -> String {
100+
try await Task.sleep(nanoseconds: 500 * 1000 * 1000)
101+
return event
102+
}
103+
}
104+
105+
let uuid = UUID().uuidString
106+
XCTAssertEqual(try Lambda.test(MyLambda.self, with: uuid), uuid)
107+
}
147108
}
109+
#endif

0 commit comments

Comments
 (0)