【问题标题】:Matching a pattern up until the next instance of that pattern匹配一个模式直到该模式的下一个实例
【发布时间】:2021-04-10 15:43:29
【问题描述】:

我正在尝试创建一个正则表达式来匹配 SSH 配置文件中的条目,该文件具有以下基本结构:

Host <Name>
    Field1 Value1
    FieldN ValueN
Host *
    Field1 Value1
    FieldN ValueN
Host !<name>
    Field1 Value1
    FieldN ValueN

关于此结构的注意事项: 缩进是可选的(我首先在我的模式中使用 \s 直到我意识到这一点)。更多细节在这里:https://linuxize.com/post/using-the-ssh-config-file/

在给定的 SSH 配置文件中可以有任意数量的主机(以及每个主机的参数/字段)。我正在努力想出正确的语法来捕获所有情况,并对事物进行适当的分组,以便我可以在我的解析代码中轻松处理它们。

看来,由于缩进是可选的,模式的“伪代码”基本上是:

匹配主机后跟空格,然后是任何有效主机名字符的行,加上!和/或 *,以换行符结尾:

(Host\s[a-zA-Z0-9-!\*]+)\n)

然后匹配任何后续行,其中空格之前的任何内容都是字段名称,第一次出现空格之后的任何内容都是该字段的值,直到下一个“Host ...”行的实例,其中点它应该是它自己的单独匹配。我已经研究过使用几个不同的标志或运算符来完成最后一部分,但我无法确切地弄清楚如何使它工作,或者这样的事情是否可能。

另一种想法是完全废弃正则表达式并为文件编写自定义解析器,逐行迭代并跟踪每个主机的选项,但正则表达式将是理想的,因为传递给我的函数的文件可能会也可能不会即使是SSH配置文件,代码也是为了确认是否是,如果是,解析相关数据。

任何关于正则表达式的指导将不胜感激!

【问题讨论】:

  • 可以获取每次出现的索引,然后根据这些索引将字符串分割成若干个子字符串
  • 谷歌快速搜索后,似乎有多个开源的 go 包用于读取和操作 ssh 配置文件

标签: regex go


【解决方案1】:

你不应该使用正则表达式。它可能会使您的解决方案复杂化并使其难以修改。你说,人类创造了一种叫做Parsers的特殊软件来解决这类问题。

在此处查看示例:https://blog.gopheracademy.com/advent-2014/parsers-lexers/

您可以在此 repo 中找到更多示例:https://github.com/danistefanovic/build-your-own-x,只需搜索 Parser 字词即可。

如果您确定要使用正则表达式,您需要将其拆分为步骤并首先对您的主机进行分组,然后逐个解析它们。要拆分它们,请参见示例正则表达式:https://regex101.com/r/NFbGxR/1

【讨论】:

  • 在正则表达式中使用[^Host] Host\s+(.*)\n((?:[^Host].*\n)+)? 表示匹配除H o st 之外的任何单个字符,并且如果字段例如以o
  • 我知道,但不幸的是,标准 go 包中不支持负前瞻。所以我发布了更好的解决方案是使用解析器 - @Thefourthbird 当你使用更复杂的正则表达式时,比在标准 go 包中实现的你可以使用类似:Host\s+(.*)\n((?:(?!Host).*\n)+)? as regex
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2014-04-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-11-16
  • 1970-01-01
  • 2014-05-21
相关资源
最近更新 更多