1

为了测试,我需要使用OpenResty在 Nginx 服务器中创建一些假数据。我需要创建一个复制一个 IP 地址的数组,例如:

 ["1.2.3.4", "1.2.3.4", ...]

在 Ruby 中,实现可能如下所示:

 "[" + (["\"1.2.3.4\""] * 4096).join(", ") + "]"

我是 Lua 的初学者,为了让它在 OpenResty 环境中工作,我付出了很多努力。这似乎终于奏效了:

   content_by_lua '
        -- ... some code ...
        local ips = {}
        for i=1,4096 do ips[i] = "\\"1.2.3.4\\"" end
        local fakeData = table.concat(ips, ", ")
        local fakeResponse = "[" .. fakeData .. "]"
        --- ...
   '

我在字符串引用方面遇到了一些问题。首先,我尝试'"1.2.3.4"'了,它在内联 Lua 部分中不起作用。这是可以理解的,因为该'字符已经是该content_by_lua部分的分隔符。

接下来,我尝试"\"1.2.3.4\""了,我希望它可以工作,但它导致了这个(令人困惑的)错误:

failed to load inlined Lua code:
content_by_lua(nginx.conf:235):17: malformed number near '1.2.3.4'

通过反复试验,我发现如果使用双引号 ( "\\"1.2.3.4\\""),这个错误就会消失。这在 OpenResty 中有效,尽管如果我在Lua REPL中尝试相同的代码会被拒绝:

$ rep.lua 
Lua REPL 0.8
> "\\"1.2.3.4\\""
[string "REPL"]:1: unexpected symbol near '"\"'

为了帮助我理解并成为一个更好的 Lua/OpenResty 程序员,我有一些关于引用的问题:

  1. 为什么需要双引号(在 OpenResty 中)?(为什么"\\"1.2.3.4\\""而不是"\"1.2.3.4\""?)
  2. 为什么 OpenResty 的行为与 Lua REPL 不同?
  3. 是否可以在content_by_lua部分中使用单引号?(将其简化为'"1.2.3.4"'

(另外,一个不相关的问题困扰着我。有没有更简单的方法来表达代码?当我将它与我的 Ruby 片段进行比较时,我很确定它也可以在 Lua 中更优雅地表达。)

4

1 回答 1

1

正如 Egor 所说,这是因为反斜杠字符\在被 Lua 解析之前被 nginx 配置文件解析器剥离了。在您的情况下,"\\"1.2.3.4\\""是正确的,因为它"\"1.2.3.4\""由 nginx 配置解析器解析,然后"1.2.3.4"由 Lua 解析为字符串。

如果您不想担心要使用多少个反斜杠,有几种选择。最简单的是使用content_by_lua_block,从 OpenResty v0.9.17 开始提供。

content_by_lua_block {
    -- ... some code ...
    local ips = {}
    for i=1,4096 do ips[i] = '"1.2.3.4"' end
    local fakeData = table.concat(ips, ", ")
    local fakeResponse = "[" .. fakeData .. "]"
    --- ...
}

如果你不能在你的 OpenResty 版本中使用 Lua 块,你可以使用 Lua 的多行字符串语法

content_by_lua '
    -- ... some code ...
    local ips = {}
    for i=1,4096 do ips[i] = [["1.2.3.4"]] end
    local fakeData = table.concat(ips, ", ")
    local fakeResponse = "[" .. fakeData .. "]"
    --- ...
'

有关更多详细信息,请参阅OpenResty 文档

此外,如果您想完全避免使用表,您可以使用string.rep.

content_by_lua '
    -- ... some code ...
    local ip = [["1.2.3.4"]]
    local fakeResponse = "[" .. string.rep(ip .. ", ", 4095) .. ip .. "]"
    --- ...
'
于 2017-05-23T02:52:37.607 回答