it-swarm.com.de

Wie verwende ich Ruby für Shell-Skripte?

Ich habe einige einfache Shell-Skriptaufgaben, die ich ausführen möchte

Beispiel: Auswählen einer Datei im Arbeitsverzeichnis aus einer Liste der Dateien, die einem regulären Ausdruck entsprechen.

Ich weiß, dass ich so etwas mit Standard Bash und Grep machen kann, aber ich wäre nett, wenn ich schnelle Skripte hacken könnte, die unter Windows und Linux funktionieren, ohne dass ich mir einen Haufen Kommandozeilenprogramme und Flags merken müsste.

Ich habe versucht, dies in Gang zu bringen, war jedoch verwirrt darüber, wo ich Informationen wie einen Verweis auf das aktuelle Verzeichnis erhalten sollte

Die Frage ist also, welche Teile der Ruby Bibliotheken muss ich kennen, um Ruby Shell-Skripte schreiben zu können?

162
Willbill

Standardmäßig haben Sie bereits Zugriff auf Dir und File , die für sich genommen sehr nützlich sind.

Dir['*.rb'] #basic globs
Dir['**/*.rb'] #** == any depth of directory, including current dir.
#=> array of relative names

File.expand_path('~/file.txt') #=> "/User/mat/file.txt"
File.dirname('dir/file.txt') #=> 'dir'
File.basename('dir/file.txt') #=> 'file.txt'
File.join('a', 'bunch', 'of', 'strings') #=> 'a/bunch/of/strings'

__FILE__ #=> the name of the current file

Ebenfalls nützlich aus der stdlib ist FileUtils

require 'fileutils' #I know, no underscore is not Ruby-like
include FileUtils
# Gives you access (without prepending by 'FileUtils.') to
cd(dir, options)
cd(dir, options) {|dir| .... }
pwd()
mkdir(dir, options)
mkdir(list, options)
mkdir_p(dir, options)
mkdir_p(list, options)
rmdir(dir, options)
rmdir(list, options)
ln(old, new, options)
ln(list, destdir, options)
ln_s(old, new, options)
ln_s(list, destdir, options)
ln_sf(src, dest, options)
cp(src, dest, options)
cp(list, dir, options)
cp_r(src, dest, options)
cp_r(list, dir, options)
mv(src, dest, options)
mv(list, dir, options)
rm(list, options)
rm_r(list, options)
rm_rf(list, options)
install(src, dest, mode = <src's>, options)
chmod(mode, list, options)
chmod_R(mode, list, options)
chown(user, group, list, options)
chown_R(user, group, list, options)
touch(list, options)

Welches ist ziemlich schön

145
webmat

Wie die anderen bereits gesagt haben, sollte Ihre erste Zeile sein

#!/usr/bin/env Ruby

Und Sie müssen es auch ausführbar machen: (in der Shell)

chmod +x test.rb

Dann folgt der Code Ruby. Wenn Sie eine Datei öffnen

File.open("file", "r") do |io|
    # do something with io
end

die Datei wird in dem aktuellen Verzeichnis geöffnet, das Sie mit pwd in der Shell erhalten würden.

Der Pfad zu Ihrem Skript ist ebenfalls einfach zu finden. Mit $0 Sie erhalten das erste Argument der Shell, das der relative Pfad zu Ihrem Skript ist. Der absolute Pfad kann folgendermaßen bestimmt werden:

#!/usr/bin/env Ruby
require 'pathname'
p Pathname.new($0).realpath()

Für Dateisystemoperationen verwende ich fast immer Pfadnamen. Dies ist ein Wrapper für viele andere Dateisystemklassen. Auch nützlich: Dir, File ...

109
Georg Schölly

In den anderen Antworten fehlt etwas Wichtiges: Die Befehlszeilenparameter werden über das ARGV-Array (global) für Ihr Ruby Shell-Skript verfügbar gemacht.

Wenn Sie also ein Skript namens my_Shell_script hatten:

#!/usr/bin/env Ruby
puts "I was passed: "
ARGV.each do |value|
  puts value
end

... mache es ausführbar (wie andere schon erwähnt haben):

chmod u+x my_Shell_script

Und nenne es so:

> ./my_Shell_script one two three four five

Du würdest folgendes bekommen:

I was passed: 
one
two
three
four
five

Die Argumente funktionieren gut mit der Dateinamenerweiterung:

./my_Shell_script *

I was passed: 
a_file_in_the_current_directory
another_file    
my_Shell_script
the_last_file

Das meiste davon funktioniert nur unter UNIX (Linux, Mac OS X), aber Sie können ähnliche (wenn auch weniger bequeme) Dinge in Windows tun.

66
Craig Walker

Hier gibt es viele gute Ratschläge, deshalb wollte ich noch ein bisschen mehr hinzufügen.

  1. Backticks (oder Back-Ticks) erleichtern das Erstellen von Skripten erheblich. Erwägen

    puts `find . | grep -i lib`
    
  2. Wenn Sie auf Probleme mit der Ausgabe von Backticks stoßen, wird das Zeug auf Standardfehler anstatt auf Standardausgabe gesetzt. Verwenden Sie diesen Rat

    out = `git status 2>&1`
    
  3. Backticks interpolieren Strings:

    blah = 'lib'
    `touch #{blah}`
    
  4. Du kannst auch in Ruby pfeifen . Es ist ein Link zu meinem Blog, aber es verlinkt hierher, also ist es in Ordnung :) Es gibt wahrscheinlich fortgeschrittenere Dinge zu diesem Thema.

  5. Wie andere angemerkt haben, gibt es Rush, wenn Sie es ernst meinen möchten: nicht nur als Shell-Ersatz (was für mich ein bisschen zu verrückt ist), sondern auch als als Bibliothek für Ihre Verwendung in Shell-Skripten und -Programmen.


Verwenden Sie auf einem Mac Applescript in Ruby für mehr Leistung. Hier ist mein Shell_here Skript:

#!/usr/bin/env Ruby
`env | pbcopy` 
cmd =  %[email protected] app "Terminal" to do script "$(paste_env)"@
puts cmd

`osascript -e "${cmd}"`
31
Dan Rosenstark

Holen Sie sich eine Kopie von Everyday Scripting with Ruby . Es enthält viele nützliche Tipps, wie Sie die Art der Dinge tun, die Sie tun möchten.

21
Aaron Hinni

Dies könnte auch hilfreich sein: http://Rush.heroku.com/

Ich habe es nicht viel benutzt, sieht aber ziemlich cool aus

Von der Website:

Rush ist ein Ersatz für die Unix-Shell (bash, zsh usw.), die eine reine Ruby) -Syntax verwendet. Durchsuchen Sie Dateien, finden und beenden Sie Prozesse, kopieren Sie Dateien - alles, was Sie jetzt in der Shell tun in Ruby

12
craigp

angenommen, Sie schreiben Ihr script.rb Skript. stellen:

#!/usr/bin/env Ruby

als erste Zeile und mache ein chmod +x script.rb

10
Vasil

Wenn Sie komplexere Ruby Skripte schreiben möchten, können diese Tools helfen:

Beispielsweise:

  • thor (ein Skript-Framework)

  • gli (git like interface)

  • Methadon (zum Erstellen einfacher Werkzeuge)

Sie bieten einen schnellen Einstieg in das Schreiben eigener Skripte, insbesondere der Befehlszeilen-App.

6
Bohr

Die obige Antwort ist interessant und sehr hilfreich, wenn ich Ruby als Shell-Skript verwende. Ich verwende Ruby als tägliche Sprache nicht und bevorzuge die Verwendung Ruby nur als Flusskontrolle und trotzdem Bash verwenden, um die Aufgaben zu erledigen.

Einige Hilfsfunktionen können zum Testen des Ausführungsergebnisses verwendet werden

#!/usr/bin/env Ruby
module ShellHelper
  def test(command)
    `#{command} 2> /dev/null`
    $?.success?
  end

  def execute(command, raise_on_error = true)
    result = `#{command}`
    raise "execute command failed\n" if (not $?.success?) and raise_on_error
    return $?.success?
  end

  def print_exit(message)
    print "#{message}\n"
    exit
  end

  module_function :execute, :print_exit, :test
end

Mit helper könnte das Ruby script ähnlich lauten:

#!/usr/bin/env Ruby
require './Shell_helper'
include ShellHelper

print_exit "config already exists" if test "ls config"

things.each do |thing|
  next if not test "ls #{thing}/config"
  execute "cp -fr #{thing}/config_template config/#{thing}"
end
4
Houcheng

Fügen Sie dies am Anfang Ihrer script.rb ein

#!/usr/bin/env Ruby

Dann markieren Sie es als ausführbar:

chmod +x script.rb
4

"Wie schreibe ich Ruby?" Geht etwas über den Rahmen von SO hinaus.

Um diese Ruby Skripte in ausführbare Skripte umzuwandeln, fügen Sie dies als erste Zeile Ihres Ruby Skripts ein:

#!/path/to/Ruby

Dann machen Sie die Datei ausführbar:

chmod a+x myscript.rb

und los gehts.

4

Die Antwort von webmat ist perfekt. Ich möchte Sie nur auf einen Zusatz hinweisen. Wenn Sie viel mit Befehlszeilenparametern für Ihre Skripte zu tun haben, sollten Sie optparse verwenden. Es ist einfach und hilft Ihnen enorm.

3
awenkhh

In Ruby ist die Konstante __FILE__ gibt Ihnen immer den Pfad des Skripts an, das Sie ausführen.

Unter Linux /usr/bin/env ist dein Freund:

#! /usr/bin/env Ruby
# Extension of this script does not matter as long
# as it is executable (chmod +x)
puts File.expand_path(__FILE__)

Unter Windows hängt es davon ab, ob mit Ruby .rb-Dateien verknüpft sind. Wenn sie sind:

# This script filename must end with .rb
puts File.expand_path(__FILE__)

Wenn dies nicht der Fall ist, müssen Sie Ruby auf ihnen explizit aufrufen, ich verwende eine Zwischen-CMD-Datei:

my_script.cmd:

@Ruby %~dp0\my_script.rb

my_script.rb:

puts File.expand_path(__FILE__)
3
bltxd