linux - 如何将 shell 脚本部署到私有(private) Linux 虚拟机

标签 linux bash azure

我有一个私有(private) Azure Linux VM,这意味着它只能从 Jumpbox(access) vm 访问。我需要将脚本部署到这个私有(private)虚拟机。由于此虚拟机甚至无法访问任何存储帐户/存储库,因此我无法使用 Custom Script Extension用于脚本部署。所以我想到使用az vm run-command invoke来部署脚本通过转换 SomeScript.sh到字符串和echo它到虚拟机。我的代码的不同部分如下:

SomeScript.sh
#!/bin/bash

#
# CommandToExecute: ./SomeScript.sh ${CUST_NO}
#
#some more code

将.sh文件转换为字符串的函数:

function getCommandToExecute()
{
    local scriptName=$1
    local commandToExecute
    local currentLocation=$(dirname "$0")
    local scriptFullPath="$currentLocation/Environment/VmScripts/$scriptName"
    mapfile < $scriptFullPath
    printf -v escapedContents "%q\n" "${MAPFILE[@]}"
    commandToExecute+="echo "$escapedContents" > /usr/myapps/$scriptName"
    echo "$commandToExecute"
}

虚拟机运行命令:

az vm run-command invoke -g $resourceGroupName \
-n $vmName --command-id RunShellScript \
--scripts "#!/bin/bash\n ${commandToExecute}"

如果我使用"#!/bin/bash\n ${commandToExecute}" commandToExecute 中的部分( RunCommand 替换为字符串脚本)在 azure 门户中的窗口中,脚本工作正常,但由于此异常,我无法通过运行命令使其工作: \n[stdout]\n\n[stderr]\n/bin/sh: 1: /var/lib/waagent/run-command/download/133/script.sh: not found\n"

知道这里缺少什么吗?或者是否有更好的替代方案来处理这个问题。

最佳答案

我认为引用整个脚本及其部署脚本以与 --scripts 一起使用是一项繁重的工作,而且也容易出错。幸运的是,这两个引用步骤都有更简单的替代方法。 documentation of az vm run-command invoke --scripts

Use @{file} to load script from a file.

因此,你可以这样做

deploymentScript() {
  echo   '#! /usr/bin/env bash'
  printf 'tail -n+4 "${BASH_SOURCE[0]}" > %q\n' "$2"
  echo   'exit'
  cat "$1"
}
deploymentScript local.sh remote.sh > tmpDeploy.sh
az vm run-command invoke ... --scripts '@{tmpDeploy.sh}'
rm tmpDeploy.sh

local.sh 替换为要部署的本地脚本的路径,并将 remote.sh 替换为应部署脚本的远程路径。

如果你幸运的话,那么你甚至可能不需要tmpDeploy.sh。尝试一下

az vm ... --scripts "@{<(deploymentScript local.sh remote.sh)}"

关于实现的一些注意事项:

  • 部署的脚本是脚本文件的精确副本。甚至嵌入的二进制数据也被保留。 tail $BASH_SOURCE 的技巧受到 this answer 的启发。 .

  • 脚本可以任意长。即使是巨大的脚本也不会遇到 getconf ARG_MAX 施加的错误 Argument list too long

关于linux - 如何将 shell 脚本部署到私有(private) Linux 虚拟机,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62346596/

相关文章:

linux - 在 Linux (Fedora Xfce) 中启动 byzanz-record 的 Bash 脚本

c++ - 如何在应用程序退出()期间处理 Qthread 终止?

linux - 如何查看Linux文件系统中使用的缓冲区/缓存的大小?

linux - 您可以使用 'less' 或 'more' 来输出一页文本吗?

bash - 如何使用部分复制的文件恢复 scp?

Azure B2C 自定义策略 + OpenID 连接 C# 库

windows - 在 Windows 上使用 Azure CLI 颁发证书链中的自签名证书

azure - 如何使用服务托管标识通过 Terraform 在 Azure 中配置资源

linux - 在 POSIX 环境中如何分配大于 0 字节的文件而不写入内容?

linux - shell 脚本中的定时陷阱