如何在 Swift 中模拟 UIApplication?
How to mock UIApplication in Swift?
我目前在 Swift 中使用 Quick + Nimble 进行单元测试。我正在构建一个 Inviter
class,它通过不同的方法发送应用程序邀请。
我需要模拟 UIApplication 以验证我的代码调用了 openURL
。
到目前为止我的代码:
import Quick
import Nimble
import OCMock
extension Inviter {
convenience init(usingMockApplication mockApplication: UIApplication) {
self.init()
application = mockApplication
}
}
class MockUIApplication : UIApplication {
var application = UIApplication.sharedApplication()
var openedURL: String?
override func openURL(url: NSURL) -> Bool {
openedURL = url.absoluteString
return true
}
}
class InviterSpec: QuickSpec {
override func spec() {
describe("Inviter") {
var mockApplication = MockUIApplication()
var inviter = Inviter(usingMockApplication: mockApplication)
beforeEach() {
inviter = Inviter(usingMockApplication: mockApplication)
}
context("for WhatsApp invites") {
beforeEach() {
inviter.inviteViaWhatsAppWithMessage("Invite Message.")
}
it("should tell the application to open WhatsApp") {
expect(mockApplication.openedURL).toNot(beNil())
}
it("should send WhatsApp the right message") {
let message = mockApplication.openedURL?.lastPathComponent
expect(message).to(equal("Invite%Message."))
}
}
}
}
}
在这种方法中,我的应用程序在运行时出错,指出只有一个 UIApplication
是可以理解的。以前,可以使 MockUIApplication
继承自 NSObject
,并将其传递进来。不幸的是,Swift 的严格类型检查似乎也阻止了这种情况。
会喜欢任何想法。
你很接近。为您需要的功能使用协议。
protocol UIApplicationProtocol {
func openURL(url: NSURL) -> Bool
}
extension UIApplication: UIApplicationProtocol {}
那么你只需要使用协议而不是 class
extension Inviter {
convenience init(usingMockApplication mockApplication: UIApplicationProtocol) {
self.init()
application = mockApplication
}
}
您需要修改 Inviter
class 才能同时使用 UIApplicationProtocol
。
我目前在 Swift 中使用 Quick + Nimble 进行单元测试。我正在构建一个 Inviter
class,它通过不同的方法发送应用程序邀请。
我需要模拟 UIApplication 以验证我的代码调用了 openURL
。
到目前为止我的代码:
import Quick
import Nimble
import OCMock
extension Inviter {
convenience init(usingMockApplication mockApplication: UIApplication) {
self.init()
application = mockApplication
}
}
class MockUIApplication : UIApplication {
var application = UIApplication.sharedApplication()
var openedURL: String?
override func openURL(url: NSURL) -> Bool {
openedURL = url.absoluteString
return true
}
}
class InviterSpec: QuickSpec {
override func spec() {
describe("Inviter") {
var mockApplication = MockUIApplication()
var inviter = Inviter(usingMockApplication: mockApplication)
beforeEach() {
inviter = Inviter(usingMockApplication: mockApplication)
}
context("for WhatsApp invites") {
beforeEach() {
inviter.inviteViaWhatsAppWithMessage("Invite Message.")
}
it("should tell the application to open WhatsApp") {
expect(mockApplication.openedURL).toNot(beNil())
}
it("should send WhatsApp the right message") {
let message = mockApplication.openedURL?.lastPathComponent
expect(message).to(equal("Invite%Message."))
}
}
}
}
}
在这种方法中,我的应用程序在运行时出错,指出只有一个 UIApplication
是可以理解的。以前,可以使 MockUIApplication
继承自 NSObject
,并将其传递进来。不幸的是,Swift 的严格类型检查似乎也阻止了这种情况。
会喜欢任何想法。
你很接近。为您需要的功能使用协议。
protocol UIApplicationProtocol {
func openURL(url: NSURL) -> Bool
}
extension UIApplication: UIApplicationProtocol {}
那么你只需要使用协议而不是 class
extension Inviter {
convenience init(usingMockApplication mockApplication: UIApplicationProtocol) {
self.init()
application = mockApplication
}
}
您需要修改 Inviter
class 才能同时使用 UIApplicationProtocol
。