session - 是否可以将当前 session 信息全局存储在vibe.d中? (dlang)

标签 session d vibed

来自网站的示例:

import vibe.d;

void login(HTTPServerRequest req, HTTPServerResponse res)
{
    enforceHTTP("username" in req.form && "password" in req.form,
        HTTPStatus.badRequest, "Missing username/password field.");

    // todo: verify user/password here

    auto session = res.startSession();
    session["username"] = req.form["username"];
    session["password"] = req.form["password"];
    res.redirect("/home");
}

void logout(HTTPServerRequest req, HTTPServerResponse res)
{
    res.terminateSession();
    res.redirect("/");
}

void checkLogin(HTTPServerRequest req, HTTPServerResponse res)
{
    // force a redirect to / for unauthenticated users
    if( req.session is null )
        res.redirect("/");
}

shared static this()
{
    auto router = new URLRouter;
    router.get("/", staticTemplate!"index.dl");
    router.post("/login", &login);
    router.post("/logout", &logout);
    // restrict all following routes to authenticated users:
    router.any("*", &checkLogin);
    router.get("/home", staticTemplate!"home.dl");

    auto settings = new HTTPServerSettings;
    settings.sessionStore = new MemorySessionStore;
    // ...
}

但是假设我不想将 ServerResponse 传递到我的程序中的每个函数中。例如,如果 res.session 存储当前用户的 id 该怎么办?这是经常使用的,所以我不希望它通过每个函数。如何在全局范围内存储此 session 信息?假设有多个用户使用该网站。

最佳答案

这是可能的,尽管有点令人沮丧。

解决方案

您不能简单地将其存储在全局范围内,因为不存在“全局” session 之类的东西 - 它始终特定于请求上下文。即使默认情况下在 D 中具有全局线程本地也无济于事,因为多个纤程共享相同的执行线程。

对于此类任务,vibe.d 提供了 TaskLocal模板,它可以完全满足您的需求。我没有尝试过,但预计 TaskLocal!Session session “只是工作”。

请注意文档中的这两个警告:

Note, however, that each TaskLocal variable will increase the memory footprint of any task that uses task local storage. There is also an overhead to access TaskLocal variables, higher than for thread local variables, but generally still O(1)

FiberLocal instances MUST be declared as static/global thread-local variables. Defining them as a temporary/stack variable will cause crashes or data corruption!

反对

但是,根据我的经验,尽管打字会带来一些不便,但最好还是显式传递所有此类上下文。不鼓励使用全局变量是有原因的——随着程序大小的增长,跟踪模块之间的依赖关系并测试此类代码将不可避免地变得困难。现在陷入便利的诱惑可能会在以后引起很多头痛。为了最大限度地减少额外的输入并简化代码维护,我可能建议改为定义 struct Context { ...}它将包含请求/ session 指针,并将定期传递。

关于session - 是否可以将当前 session 信息全局存储在vibe.d中? (dlang),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20482187/

相关文章:

d - 使用 response.render 渲染模板文件时,使用 Vibe.d 的变量

Linux - 加入两个独立的 SSH 连接

php - 人们使用 PHP session 登录随机用户帐户

node.js - NodeJS + MongoDB + Redis : Register and login - sessions issue

php - setcookie() 和 session_set_cookie_params() 函数之间的区别

rest - D 中的 REST 框架有哪些选择?

python - D 编程语言中的 UDP 套接字

file-io - 延迟读取 D 中的文件

user-interface - 如何从控制台或 GUI 应用程序检测是否运行?

multithreading - Vibe.D 是多线程来处理并发请求的吗?