1

我在使用正则表达式从 HTTP 标头中可靠地提取 URL 时遇到了麻烦。带有和不带有似乎与空白类不匹配的 ^M 字符交替到达的标题并没有帮助。目前我迄今为止管理的最好的是:

(re-search-forward "^x-url: .*/\\{2,3\\}\\(.*\\)" nil t)

但是,当然,如果它存在 ^M 以及我并不真正需要的 URL 参数,它也会得到它。给你一个我调试的例子:

x-url: http://wiki/mediawiki/index.php?title=Vsmux&action=edit&redlink=1
x-url: http://wiki/mediawiki/index.php?title=Vsmux&action=edit&redlink=1^M

在这两种情况下我真正想要的只是结果:

wiki/mediawiki/index.php
4

3 回答 3

3

这看起来很可怕,但我不对它的外观负责——发明这个愚蠢标准的人是......但这应该非常严格地遵循标准(旧版本,不包括 Unicode 字符及其翻译):

"^x-url:\\s-*\\(\\w\\|\\+\\|-\\)+://\\(\\w\\|\\-\\)+\\(\\.\\w+\\)?\\(\\/\\(%[0-9a-fA-F]\\{2\\}\\|[~\\.A-Za-z_+-]*\\)*\\)*"

除非某些“有用的”程序已经将百分比编码的 URI 组件转换为其原始的非编码形式。

此外,对于 URL 的部分长度可能存在一些技术限制,我不会尝试实现它......

此外,它假定从不使用基本身份验证中的身份验证方案。否则,不使用正则表达式会容易得多。

于 2012-09-26T19:07:37.213 回答
2

像这样的东西怎么样(这假设所有网址都包含“://”):

(re-search-forward "^x-url: [^:]*://\\([^?\r\n]+\\).*?$")
于 2012-09-26T17:34:51.113 回答
2

为了完整起见,我可能应该添加另一个我尝试过的解决方案,该解决方案基于与@wvxvw 关于使用正确解析器的讨论。这使得 elisp 代码看起来有点像这样:

(save-excursion
  (let* ((url-string (url-get-url-at-point (re-search-forward "^x-url: ")))
         (url (url-generic-parse-url url-string))
         (arg-split (string-match-p "?" (url-filename url))))
    (format "%s%s" (url-host url)
        (if arg-split
            (substring (url-filename url) 0 arg-split)
          (url-filename url)))))
于 2012-09-27T16:00:07.137 回答