如何用sed编辑url字符串

时间:2016-12-13 21:09:27

标签: bash url sed

我的Linux存储库文件包含一个链接,该链接到目前为止使用带有端口号的http指向它的存储库。

baseurl = http://host.domain.com:123/folder1/folder2

我现在需要一种方法来替换该URL以使用没有端口或不同端口的https。 我还需要更改服务器名称,例如从host.domain.com更改为host2.domain.com

所以我的想法是使用sed来搜索http的开头直到第一个/来自2之后//因此捕捉到它们之间的任何内容并且将使我能够更改服务器名称端口或http \ s的使用。

我现在正在使用此代码(我只使用echo作为示例):

该示例显示了在一种情况下,我有一个链接,http和端口123转换为https,第二次反过来 由于一般原因,我的两个代码都使用相同的sed。

WANTED_URL="https://host.domain.com"
echo 'http://host.domain.com:123/folder1/folder2' | sed -i "s|http.*://[^/]*|$WANTED_URL|"

OR

WANTED_URL="http://host.domain.com:123"
echo 'https://host.domain.com/folder1/folder2' | sed -i    "s|http.*://[^/]*|$WANTED_URL|"

是这样做的正确方法吗?

2 个答案:

答案 0 :(得分:2)

默认情况下,

sed正则表达式是贪婪的。您可以告诉sed仅使用非斜杠,如下所示:

 echo  'http://host.domain.com:123/folder1/folder2' | sed -e 's|http://[^/]*|https://host.domain.com|'

结果:

https://host.domain.com/folder1/folder2

(顺便说一下,你不必因为你使用的是另一个分隔字符而逃避斜线)

密钥正在使用[^/]*,它将匹配任何斜杠,因此它会在第一个斜杠处停止匹配(非贪婪)。

您使用/.*/.*可以包含斜杠,而不是您想要的(默认为贪婪)。

无论如何,我的方法是不同的,因为表达式不包括尾部斜杠,所以它不会从最终输出中删除。

答案 1 :(得分:1)

假设您有1个sed脚本或2个并不是真的重要,并且没有充分理由对URL进行硬编码:

$ echo 'http://host.domain.com:123/folder1/folder2' |
    sed 's|\(:[^:]*\)[^/]*|s\1|'
https://host.domain.com/folder1/folder2

$ port='123'; echo 'https://host.domain.com/folder1/folder2' |
    sed 's|s\(://[^/]*\)|\1:'"$port"'|'
http://host.domain.com:123/folder1/folder2

如果那不是你需要的,那么编辑你的问题以澄清你的要求,特别解释原因:

  1. 您想使用硬编码的网址,
  2. 您需要一个脚本来进行两种转换。
  3. 并提供简明,可测试的样本输入和预期输出,以证明这些需求(即上述情况不起作用的情况)。

    你有什么:

    WANTED_URL="https://host.domain.com"
    echo 'http://host.domain.com:123/folder1/folder2' | sed -i "s|http.*://[^/]*|$WANTED_URL|"
    

    主要问题是:

    1. 不要对非导出的shell变量名使用全大写,以避免与导出的变量发生冲突,并避免模糊代码(此约定已存在40年,因此人们期望所有大写变量都是出口)。
    2. 永远不要将任何脚本用双引号括起来,因为它会在您要执行的命令甚至看到它之前将整个脚本公开给shell进行解释。相反,只需在必要时打开最小脚本段周围的单引号,即在脚本中展开$y使用cmd 'x'"$y"'z'而不是cmd "x${y}z",因为后者将在加密和危险的情况下失败并给出各种输入,脚本文本,环境设置和/或运行它的目录的内容。
    3. sed的-i选项是就地编辑文件,因此您无法在传入管道上使用它,因为您无法就地编辑管道。
    4. 当你让shell变量扩展成为脚本的一部分时,你必须注意它包含的可能的字符以及在给定变量扩展的上下文的情况下它们将如何解释它们。如果您将整个URL扩展到sed脚本的替换部分,那么您必须小心首先转义任何潜在的反向引用字符或脚本分隔符。见Is it possible to escape regex metacharacters reliably with sed。如果你只是让端口号扩展,那么你就不必处理任何一个。