Javascript'te kabuk komutu nasıl çalıştırılır


127

Sistem kabuğu komutlarını ( lsörneğin) çalıştıracak ve değeri döndürecek bir JavaScript işlevi yazmak istiyorum .

Bunu nasıl başarırım?


4
bu komutu istemci veya sunucu üzerinde nerede çalıştırmak istersiniz?
Jan Hančič

Hangi işletim sistemini kullanıyorsunuz?
Anderson Yeşil

Bir kabuk komut dosyası için node.js kullanarak nasıl yapılacağına dair bir öğretici: Dreamsyssoft.com/javascript-shell-scripting/shell-tutorial.php
Rocky Pulley

7
Neden en sevilmeyen yanıtı en iyi yanıt olarak seçtiniz? o.0
André Levy

Lütfen hangi javascript türü konusunda daha spesifik olun. Bu, sunucu tarafı javascript'te mümkündür, ancak istemci tarafında javascript için imkansızdır.
Raymond Peng

Yanıtlar:


132

Buradaki diğer yanıtların çoğu, tarayıcıda çalışan bir JavaScript işlevi açısından bu sorunu ele alıyor gibi görünüyor. Soruyu soran kişi "Kabuk Komut Dosyası" dediğinde bir Node.js arka uç JavaScript'i kastettiğini varsayarak çekim yapacağım ve yanıtlayacağım. Kodunuzu çerçevelemek için muhtemelen commander.js kullanılıyor :)

Kullanabilirsin child_process düğümün API gelen modülü. Aşağıdaki örnek kodu yapıştırdım.

var exec = require('child_process').exec, child;

child = exec('cat *.js bad_file | wc -l',
    function (error, stdout, stderr) {
        console.log('stdout: ' + stdout);
        console.log('stderr: ' + stderr);
        if (error !== null) {
             console.log('exec error: ' + error);
        }
    });
 child();

Bu yardımcı olur umarım!


14
Bir şey dışında. "Çocuk bir işlev değil" hatasını alırsınız. Exec () çağrısı komutu yürütür - child () çağrısına gerek yoktur. Maalesef, geri arama, çocuk sürecin çıkaracağı bir şey olduğunda çağrılmaz - yalnızca alt süreç çıktığı zaman çağrılır. Bazen sorun değil, bazen değil.
John Deighan

2
Geri aramalardan kaçınmak için execSync'i kullanabilirsiniz .
Dan Dascalescu

1
Tarayıcıdan kim bahsetti? Sadece JavaScript diyor, daha fazlası değil.
Virus721

49

... birkaç yıl sonra ...

ES6 bir standart olarak kabul edildi ve ES7 köşeyi dönünce bu yüzden güncellenmiş yanıtı hak ediyor. Örnek olarak nodejs + babel ile ES6 + async / await kullanacağız, önkoşullar:

Örnek foo.jsdosyanız şöyle görünebilir:

import { exec } from 'child_process';

/**
 * Execute simple shell command (async wrapper).
 * @param {String} cmd
 * @return {Object} { stdout: String, stderr: String }
 */
async function sh(cmd) {
  return new Promise(function (resolve, reject) {
    exec(cmd, (err, stdout, stderr) => {
      if (err) {
        reject(err);
      } else {
        resolve({ stdout, stderr });
      }
    });
  });
}

async function main() {
  let { stdout } = await sh('ls');
  for (let line of stdout.split('\n')) {
    console.log(`ls: ${line}`);
  }
}

main();

Babel olduğundan emin ol:

npm i babel-cli -g

En son ön ayarı yükleyin:

npm i babel-preset-latest

Şununla çalıştırın:

babel-node --presets latest foo.js

3
Yalnızca hızlı bir komut yürütmeniz gerekiyorsa, tüm zaman uyumsuz / bekleme süresi aşırıdır. Sadece execSync'i kullanabilirsiniz .
Dan Dascalescu

Kimse bir Node.js çözümü istemedi. Yalnızca JavaScript diyor.
Virus721

43

Önceki cevapların neden her türlü karmaşık çözümü verdiğini bilmiyorum. Sadece gibi hızlı bir komut çalıştırmak istiyorsanız ls, async / await veya geri aramalara veya herhangi bir şeye ihtiyacınız yoktur. İşte ihtiyacınız olan her şey - execSync :

const execSync = require('child_process').execSync;
// import { execSync } from 'child_process';  // replace ^ if using ES modules
const output = execSync('ls', { encoding: 'utf-8' });  // the default is 'buffer'
console.log('Output was:\n', output);

Hata işleme için, ifadenin etrafına bir try/ catchblok ekleyin .

Tamamlanması uzun süren bir komut çalıştırıyorsanız, evet, zaman uyumsuzexec işleve bakın.


19

Bu tamamen JavaScript ortamına bağlıdır. Lütfen detaylandırın.

Örneğin, Windows Komut Dosyalarında aşağıdaki gibi şeyler yaparsınız:

var shell = WScript.CreateObject("WScript.Shell");
shell.Run("command here");

18
Linux gibi Unix benzeri bir işletim sisteminde aynı şeyi yapmak mümkün müdür?
Anderson Yeşil

bu komutu nasıl çalıştırırız: yönlendirmeyi yazdır -4 | \ "TAP-Windows Bağdaştırıcısı \" bul ?? denedim ama hiçbir şey
dönmedi

1
Ben de bunu arıyordum. Node.js hakkında konuşan tüm bu insanlar sinir bozucu. Node.js'yi burada kim istedi? Kimse yapmadı.
Virus721

JavaScript bir tarayıcının içindeyse bu çalışır mı?
Ali Sajjad

14

Kısaca:

// Instantiate the Shell object and invoke its execute method.
var oShell = new ActiveXObject("Shell.Application");

var commandtoRun = "C:\\Winnt\\Notepad.exe";
if (inputparms != "") {
  var commandParms = document.Form1.filename.value;
}

// Invoke the execute method.  
oShell.ShellExecute(commandtoRun, commandParms, "", "open", "1");


5
Bunun hangi web tarayıcısında çalıştığı üzerinde pek çok el sıkışması var gibi görünüyor, ancak millet JavaScript'in aynı zamanda mükemmel bir Windows kabuk komut dosyası dili olduğunu anlamalı.
Craig

6

NodeJS ile bu kadar basit! Ve bu komut dosyasını sunucunuzun her açılışında çalıştırmak istiyorsanız, sonsuza kadar hizmet uygulamasına bir göz atabilirsiniz !

var exec = require('child_process').exec;

exec('php main.php', function (error, stdOut, stdErr) {
    // do what you want!
});

Geri aramaları önlemek için, hızlı komutlar için execSync'i kullanabilirsiniz .
Dan Dascalescu

5

Not: Bu yanıtlar, tarayıcı tabanlı bir istemciden Unix tabanlı bir web sunucusuna doğrudur.

İstemcide komut çalıştır

Aslında yapamazsınız. Güvenlik, yalnızca bir tarayıcı içinde çalıştığını ve komutlara ve dosya sistemine erişiminin sınırlı olduğunu söylüyor.

Sunucuda ls çalıştır

Bir GET aracılığıyla parametrelerinizde geçen dinamik bir sayfayı almak için bir AJAX çağrısı kullanabilirsiniz.

Bunun bir güvenlik riski yarattığını unutmayın, çünkü Bayan Rouge hacker'ın uygulamanızı çalıştır: / dev / null && rm -rf / ......

Özetle, JS'den kaçmak sadece kötü, kötü bir fikir .... YMMV


Esasen tarayıcılar arası bir şekilde yapamazsınız . Yalnızca IE'nin kabuğa kancaları olduğuna inanıyorum (WSript / ActiveX aracılığıyla).
Justin Johnson


3

IE'de bunu yapabilirsiniz:

var shell = new ActiveXObject("WScript.Shell");
shell.run("cmd /c dir & pause");

3

İşte ifconfigLinux'un kabuk komutunu çalıştıran basit bir komut

var process = require('child_process');
process.exec('ifconfig',function (err,stdout,stderr) {
    if (err) {
        console.log("\n"+stderr);
    } else {
        console.log(stdout);
    }
});

Geri aramalardan kaçınmak için execSync'i kullanabilirsiniz .
Dan Dascalescu

3
function exec(cmd, handler = function(error, stdout, stderr){console.log(stdout);if(error !== null){console.log(stderr)}})
{
    const childfork = require('child_process');
    return childfork.exec(cmd, handler);
}

Bu işlev aşağıdaki gibi kolayca kullanılabilir:

exec('echo test');
//output:
//test

exec('echo test', function(err, stdout){console.log(stdout+stdout+stdout)});
//output:
//testtesttest

1

Nashorn ile şöyle bir senaryo yazabilirsiniz:

$EXEC('find -type f');
var files = $OUT.split('\n');
files.forEach(...
...

ve çalıştırın:

jjs -scripting each_file.js

0

Npm kullanıyorsanız shelljs paketini kullanabilirsiniz.

Yüklemek: npm install [-g] shelljs

var shell = require('shelljs');
shell.ls('*.js').forEach(function (file) {
// do something
});

Daha fazlasını görün: https://www.npmjs.com/package/shelljs

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.