nodejs child.exec bash参数为空

发布于 2025-02-08 15:09:30 字数 4791 浏览 1 评论 0原文

我正在运行一个类似的脚本:

const someString = "text@ip:ip,text@ip:,";
const arg2 = "5";
let result = await new Promise((resolve, reject) => {
        child.exec(`"/path/to/script.sh" "${someString}" "${arg2}"`,
        (error=child.ExecException, stdout=string, stderr=string) => {
            if (error) {
                isErr = true;
                reject(error);
            }else {
                resolve(stdout); 
            }
        });
    });

脚本接收arg2罚款为$ 2。但是,$ 1显示一个空白字符串。我已经在我的node.js应用程序中记录了字符串,这是正确的。可能与字符串中的特殊字符有关吗?

相对于应用程序,需要异步运行脚本,并且相对于其父函数同步运行(在上面的代码段中是这种情况)。

编辑: 这是我无法使用的原始代码。它是动态生成一个可行的库存。

nodejs:

async function buildInventory(site){
    const agentNumber = site.agentData.agentNumber;
    let hostsByType = {};
    let hosts = "";
    if ( site.hosts.length > 0 ){
        site.hosts.forEach(host => {
            if (hostsByType.hasOwnProperty(`${host.type}`)) {
                hostsByType[`${host.type}`].push(`${host.ip}`);
            }else{
                hostsByType[`${host.type}`] = [ `${host.ip}` ];
            }
        });
    }
    if ( hostsByType != {} ){
        for (const key in hostsByType) { // create arg in format type@ip:,type@ip:ip:,
        if (Object.hasOwnProperty.call(hostsByType, key)) {
            hosts = hosts + `${key}@`;
            hostsByType[key].forEach(ip => {
                hosts = hosts + `${ip}:`;
            });
            hosts = hosts + ',';
        }
        console.log(hosts); // string logged is in expected format
    }
}
    if ( hosts = "" ){
        hosts = "na";
    }
    let isErr = false;
    let result = await new Promise((resolve, reject) => {
        child.exec(`"/usr/raindrop/app/ansible/mkinv" "${hosts}" "${agentNumber}"`,
        (error=child.ExecException, stdout=string, stderr=string) => {
            if (error) {
                isErr = true;
                reject(error);
            }else {
                resolve(stdout); 
            }
        });
    });
    if( !isErr ){
        result = result.split(/\r?\n/)[0];
        if ( result == "genskipped" ){
            logger.log('info', `Inventory generation skipped(no hosts)`);
            return true;
        }else if ( result == "gensuccess"){
            logger.log('info', `Inventory generated`);
            return true;
        }else {
            logger.log('warn', `Unknown response from inventory generation script`);
            console.log(result);
            return false;
        }
    }else{
        logger.log('error', `Inventory generation error: ${result}`);
        return false;
    }
}

bash脚本:

#!/bin/bash
mkdir -p /data/ansible/$2
cd /data/ansible/$2
while [[ $1 == "na" ]];do
    echo "genskip"
    exit 0;
done
touch inventory.yml
echo "all:" > inventory.yml
echo "  children:" >> inventory.yml
IFS=',' read -a hostsByType <<< "$1" # arg in format type@ip:,type@ip:ip:,
echo $1 >> /logs/ansible-debug.log
for val in "$hostsByType";do
    while [[ "$val" != "" ]];do
        IFS='@' read -a data <<< "$val"
        echo "    ${data[0]}:" >> inventory.yml
        IFS=':' read -a hosts <<< "${data[1]}"
        c=1
        for host in "$hosts";do
            while [[ "$host" != "" ]];do
              echo "      host${c}: $host"
              c=$(($c + 1))
              break;
            done
        done
      break;
    done
done
subnet=$(cat /data/vpn/rain.conf | grep 'ipv4=')
IFS='=' read -a arr <<< $subnet
subnet=${arr[1]}
agent_ip="${subnet}${2}"
echo "  vars:"  >> inventory.yml
echo "    ansible_port: 22" >> inventory.yml
echo "    ansible_user: sisadm" >> inventory.yml
echo "    private_key_file: /data/ssh/keys/$2" >> inventory.yml
echo "    ansible_ssh_common_args: '-o StrictHostKeyChecking=no -o ProxyCommand=\"ssh -o \'ForwardAgent yes\' agent@$agent_ip -p 11522 \'ssh-add /home/agent/.ssh/id_rsa && nc %h %p\'\"'" >> inventory.yml
echo "gensuccess"

edit2: /logs/asible-debug.log每次运行脚本时都会显示一条新行。 库存。脚本创建:

all:
  children:
  vars:
    ansible_port: 22
    ansible_user: sisadm
    private_key_file: /data/ssh/keys/2
    ansible_ssh_common_args: '-o StrictHostKeyChecking=no -o ProxyCommand="ssh -o \'ForwardAgent yes\' [email protected] -p 11522 \'ssh-add /home/agent/.ssh/id_rsa && nc %h %p\'"'

I'm running a script like so:

const someString = "text@ip:ip,text@ip:,";
const arg2 = "5";
let result = await new Promise((resolve, reject) => {
        child.exec(`"/path/to/script.sh" "${someString}" "${arg2}"`,
        (error=child.ExecException, stdout=string, stderr=string) => {
            if (error) {
                isErr = true;
                reject(error);
            }else {
                resolve(stdout); 
            }
        });
    });

The script receives arg2 fine as $2. However, $1 shows a blank string. I've logged the string in my Node.js app and it is correct. Possibly something to do with special characters in the string?

The script need to be run asynchronously relative to the application and synchronously relative to it's parent function(which is the case in the code snippet above).

EDIT:
Here is the original code that I can't get working. It is to dynamically generate an ansible inventory.

nodejs:

async function buildInventory(site){
    const agentNumber = site.agentData.agentNumber;
    let hostsByType = {};
    let hosts = "";
    if ( site.hosts.length > 0 ){
        site.hosts.forEach(host => {
            if (hostsByType.hasOwnProperty(`${host.type}`)) {
                hostsByType[`${host.type}`].push(`${host.ip}`);
            }else{
                hostsByType[`${host.type}`] = [ `${host.ip}` ];
            }
        });
    }
    if ( hostsByType != {} ){
        for (const key in hostsByType) { // create arg in format type@ip:,type@ip:ip:,
        if (Object.hasOwnProperty.call(hostsByType, key)) {
            hosts = hosts + `${key}@`;
            hostsByType[key].forEach(ip => {
                hosts = hosts + `${ip}:`;
            });
            hosts = hosts + ',';
        }
        console.log(hosts); // string logged is in expected format
    }
}
    if ( hosts = "" ){
        hosts = "na";
    }
    let isErr = false;
    let result = await new Promise((resolve, reject) => {
        child.exec(`"/usr/raindrop/app/ansible/mkinv" "${hosts}" "${agentNumber}"`,
        (error=child.ExecException, stdout=string, stderr=string) => {
            if (error) {
                isErr = true;
                reject(error);
            }else {
                resolve(stdout); 
            }
        });
    });
    if( !isErr ){
        result = result.split(/\r?\n/)[0];
        if ( result == "genskipped" ){
            logger.log('info', `Inventory generation skipped(no hosts)`);
            return true;
        }else if ( result == "gensuccess"){
            logger.log('info', `Inventory generated`);
            return true;
        }else {
            logger.log('warn', `Unknown response from inventory generation script`);
            console.log(result);
            return false;
        }
    }else{
        logger.log('error', `Inventory generation error: ${result}`);
        return false;
    }
}

bash script:

#!/bin/bash
mkdir -p /data/ansible/$2
cd /data/ansible/$2
while [[ $1 == "na" ]];do
    echo "genskip"
    exit 0;
done
touch inventory.yml
echo "all:" > inventory.yml
echo "  children:" >> inventory.yml
IFS=',' read -a hostsByType <<< "$1" # arg in format type@ip:,type@ip:ip:,
echo $1 >> /logs/ansible-debug.log
for val in "$hostsByType";do
    while [[ "$val" != "" ]];do
        IFS='@' read -a data <<< "$val"
        echo "    ${data[0]}:" >> inventory.yml
        IFS=':' read -a hosts <<< "${data[1]}"
        c=1
        for host in "$hosts";do
            while [[ "$host" != "" ]];do
              echo "      host${c}: $host"
              c=$(($c + 1))
              break;
            done
        done
      break;
    done
done
subnet=$(cat /data/vpn/rain.conf | grep 'ipv4=')
IFS='=' read -a arr <<< $subnet
subnet=${arr[1]}
agent_ip="${subnet}${2}"
echo "  vars:"  >> inventory.yml
echo "    ansible_port: 22" >> inventory.yml
echo "    ansible_user: sisadm" >> inventory.yml
echo "    private_key_file: /data/ssh/keys/$2" >> inventory.yml
echo "    ansible_ssh_common_args: '-o StrictHostKeyChecking=no -o ProxyCommand=\"ssh -o \'ForwardAgent yes\' agent@$agent_ip -p 11522 \'ssh-add /home/agent/.ssh/id_rsa && nc %h %p\'\"'" >> inventory.yml
echo "gensuccess"

EDIT2:
/logs/ansible-debug.log shows a new line every time the script is run.
The inventory.yml the script creates:

all:
  children:
  vars:
    ansible_port: 22
    ansible_user: sisadm
    private_key_file: /data/ssh/keys/2
    ansible_ssh_common_args: '-o StrictHostKeyChecking=no -o ProxyCommand="ssh -o \'ForwardAgent yes\' [email protected] -p 11522 \'ssh-add /home/agent/.ssh/id_rsa && nc %h %p\'"'

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

忘羡 2025-02-15 15:09:30

您的问题在这里:

if ( hosts = "" ){
    hosts = "na";
}

尝试以下操作:

if ( hosts == "" ){
    hosts = "na";
}

Your issue is here:

if ( hosts = "" ){
    hosts = "na";
}

Try this:

if ( hosts == "" ){
    hosts = "na";
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文