【问题标题】:Passing Varnish struct variables across VCL reloads跨 VCL 重新加载传递 Varnish 结构变量
【发布时间】:2021-06-10 22:38:26
【问题描述】:

我构建了一个 Varnish VMOD,它定义了一个对象,该对象在 vcl_init 中实例化,并始终保存在内存中,并用于单个请求。

我的配置分为几个 VCL 文件,这些文件根据一些请求参数从“主”VCL 加载。

主 VCL 还实例化有问题的对象,我想在另一个 VCL 中使用它。我不在同一个 VCL 中实例化对象的原因是我有另一个 VCL,它定义了一些 ACL 限制的路由来从数据源更新对象。

例如master.vcl:

sub vcl_init {
    new myobj = mymodule.myobject();
}

sub vcl_recv {
    if (req.url ~ "^pub/") {
        return (vcl (pub_vcl));
    }
    // Other switches...
}

pub.vcl:

sub vcl_recv {
    if myobj.mymethod() {
        set req.http.x-bogus = "true";
    }
}

但在这种情况下,编译失败是因为myobjpub.vcl 中未定义,这意味着它没有从master.vcl 携带。

我还考虑在加载 pub.vcl 之前在 master.vcl 中添加测试和标头设置,但这不会起作用,因为加载 VCL 调用 std.rollback(req) 会取消设置所有请求标头,这是唯一可访问的变量在vcl_recv

有没有办法在 VCL 重新加载时传递此状态?

谢谢。

【问题讨论】:

    标签: varnish varnish-vcl


    【解决方案1】:

    您不能直接对对象执行此操作,因为它们由 VCL 限定并且不能“转义”它。如您所见,您需要先加载带标签的vcl,因此您还需要在其中创建对象。

    但没有什么能阻止您创建引用全局变量的对象,以便所有对象都可以访问相同的数据。

    或者,您可以使用Event 函数来使用PRIV_VCL (https://stackoverflow.com/a/60753085) 也引用全局指针并完全避免使用对象。这就是这里所做的,例如:https://github.com/varnish/varnish-modules/blob/master/src/vmod_vsthrottle.c#L345

    【讨论】:

    • 谢谢。由于两种解决方案都使用相同类型的存储,我将尝试第一个看起来不那么具有侵入性的存储。但是了解事件函数也很好。
    猜你喜欢
    • 1970-01-01
    • 2012-06-03
    • 2011-02-13
    • 2015-02-12
    • 2014-03-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多