XCTest 中未保留经过身份验证的 Vapor 会话 [英] Authenticated Vapor session not preserved inside an XCTest

查看:22
本文介绍了XCTest 中未保留经过身份验证的 Vapor 会话的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

应用程序本身运行良好,但我无法通过测试来确认这一点.

The application itself works fine, but I can't get a test to work that confirms this.

在下面的第 1 部分中,测试检查使用电子邮件和(正确的)密码登录是否成功,并返回正确的 URL 重定向.在重定向返回测试之前的代码中,调试显示对 request.auth.require(User.self) 的调用成功.

In Part 1 below, the test checks that the login using email and (correct) password succeeds and the correct URL redirection is returned. In the code immediately before the redirection returns to the test, debug shows that a call to request.auth.require(User.self) succeeds.

在第 2a 部分和第 2b 部分中,XCTAssertEqual 失败,日志显示对 request.auth.require(User.self) 的调用结果已抛出显示用户未获授权的错误.

In both Parts 2a and 2b, the XCTAssertEqual fails and the log shows that the result of the call to request.auth.require(User.self) has thrown an error saying the user is not authorised.

第 3 部分再次检查第 1 部分是否正常工作,因为它也会为失败的登录返回正确的 URL 重定向.

Part 3 is a double-check that Part 1 is working as it, too, returns the correct URL redirection for an unsuccessful login.

因此,似乎除了对 .test(...) 的调用之外,会话数据没有被保留.有没有办法解决这个问题?

So, it seems that the session data is not being preserved beyond the call to .test(...). Is there a way around this?

@testable import App
import XCTVapor
final class AppTests: XCTestCase
{
    func test011UserLoginLogout() throws
    {
        func attemptLogin(withPassword password:String, completion:(XCTHTTPResponse) throws -> ()) throws -> Void
        {
            var body = ByteBufferAllocator().buffer(capacity: 0)
            body.writeString(#"{"email":"me@example.com","password":"\#(password)"}"#)
            var headers = HTTPHeaders()
            headers.replaceOrAdd(name: .contentLength, value: body.readableBytes.description)
            headers.contentType = .json
            try app.test(.POST, "/login", headers:headers, body:body) { response in try completion( response ) }
        }

        var app = Application(.testing)
        app.databases.use(.mysql(hostname:DBHost, username:DBAccount, password:DBPassword, database:DBDatabase, tlsConfiguration:.none), as:.mysql)
        app.databases.default(to:.mysql)
        do { try configure(app!) }
        catch { XCTFail("configure(app) failed") }
        //  Part 1 succeeds
        try attemptLogin(withPassword:"goodPassword")
        {
            res in
            XCTAssertEqual(res.status, HTTPResponseStatus.seeOther)
            XCTAssertEqual(res.headers["location"].first,"success")
            try app!.test(.GET, "/success")
            {
                response in
                XCTAssertEqual(response.status, .ok) // <--- Part 2(a) fails
            }
        }

        try app.test(.GET, "/success")
        {
            response in
            XCTAssertEqual(response.status, .ok) // <-- Part 2(b) fails
        }

        // Part 3 succeeds
        try attemptLogin(withPassword:"badPassword")
        {
            response in
            XCTAssertEqual(response.status, .seeOther)
            XCTAssertEqual(response.headers["location"].first,"failed")
        }
    }
}

推荐答案

我认为您在失败的请求中缺少身份验证.如果使用会话,您需要将会话 cookie 传递到失败的请求中,或者如果使用不记名身份验证,则需要将令牌传递给失败的请求.

I think you're missing the authentication in the request that are failing. You either need to pass the session cookie into the failing request if using sessions or the token if using bearer auth.

这篇关于XCTest 中未保留经过身份验证的 Vapor 会话的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆