sys methods

The sys object, which is accessible from anywhere in an Rantfile, provides many methods for common file system operations like deleting, copying, moving, comparing and writing files.

Unless explicitely mentioned otherwise, the following statements apply to all below documented methods:

  1. Portable across all supported platforms.
  2. Ignore the return value!
  3. The messages printed to standard output may change.
  4. Error conditions are reported through exceptions of class SystemCallError or subclasses of SystemCallError.

The following methods print messages to standard output:

  • cd(dir)

    Change the current directory to dir. dir may be an absolute path or a path relative to the current directory. If a block is given, the current directory will be changed to dir, then the block is executed and it is ensured, that after block execution the old working directory is resumed (even if an exception is thrown during block execution).

    Examples:

      # relative path
      sys.pwd             # => "/home/user"
      sys.cd "tmp"        # prints "cd tmp"
      sys.pwd             # => "/home/user/tmp"
      sys.cd ".."         # prints "cd .."
      sys.pwd             # => "/home/user"
    
      # absolute path
      sys.cd "/etc"       # prints "cd /etc"
      sys.pwd             # => "/etc"
    
      # relative path, with block
      sys.pwd             # => "/home/user"
      sys.cd "tmp" do
          sys.pwd         # => "/home/user/tmp"
          # perform some operations, may
          # also call sys.cd
          sys.cd "/etc"
      end
      sys.pwd             # => "/home/user"
    
  • rm(file)

    Remove file. file may be an absolute or relative path (string). If file is an array of strings or a filelist, remove all entries of file.

    Examples:

      # remove the file "util.o" in the current directory
      sys.rm "util.o"     # prints "rm util.o"
    
      # remove all files ending in ".o" in the "lib" directory
      sys.rm sys["lib/*.o"]
    

    Raises a SystemCallError if file doesn’t exist or is a directory.

  • rm_f(file)

    Same as rm(file), but doesn’t throw an exception if file doesn’t exist.

    Example:

      # remove "main.o" if it exists
      sys.rm_f "main.o"   # prints "rm -f main.o"
    
  • rmdir(dir)

    Remove the empty directory dir. dir may be a list of strings, a filelist or a string. Raises a SystemCallError if dir is not empty or doesn’t exist.

    Examples:

      # remove empty directory "/home/user/tmp"
      sys.rmdir "/home/user/tmp"
    
      # remove empty directory, relative path
      sys.rmdir "tmp"
    
      # remove empty directories "tmp" and "/usr/local/tmp"
      sys.rmdir ["tmp", "/usr/local/tmp"]
    
      # remove all (empty) directories in the current directory ending
      # in ".t"
      sys.rmdir sys["*.t"]
    
  • rm_r(entry)

    If entry is a (relative or absolute) path to a file, simply removes the file. If entry is a directory, remove the directory and all its contents (including subdirectories).

    If entry is an array of pathes or a filelist, remove all entries listed in entry (directories are removed, including their contents, too).

    Examples:

      # remove the "tmp" directory and all its contents
      sys.rm_r "tmp"      # prints "rm -r tmp"
    

    Raises a SystemCallError if entry doesn’t exist.

  • rm_rf(entry)

    Does the same as rm_r(entry), but doesn’t raise an exception if entry doens’t exist.

    Example:

      # remove the "tmp" directory and all its contents if it exists
      sys.rm_rf "tmp"     # prints "rm -rf tmp"
    
  • mkdir(dir)

    If dir is a string, create the new directory dir. dir may be a relative or absolute path.

    Examples:

      # relative path
      sys.mkdir "foo"
    
      # absolute path
      sys.mkdir "/home/user/foo"
    

    If dir is a list of strings, or a filelist, create all directories listed in dir.

    Example:

      # with array, creates directory "foo" and directory "bar"
      sys.mkdir ["foo", "bar"]
    

    Raises a SystemCallError if a file/directory with this name already exists.

  • mkdir_p(dir)

    Creates the directory dir and all its parent directories, if necessary. Does nothing if dir already exists.

    If dir is an array/filelist, creates all directories listed in dir.

    Examples:

      # creates "/usr" if a directory of this name doesn't exist
      # creates "/usr/local" if a directory of this name doesn't exist
      # creates "/usr/local/bin" if a directory of this name doesn't exist
      sys.mkdir_p "/usr/local/bin"    # prints "mkdir -p /usr/local/bin"
    
      # creates the three given pathes
      sys.mkdir_p ["foo/include", "foo/src/util", "foo/src/ui"]
    
  • cp(src, dest)

    If src is a (relative or absolute) path to a file, copy the file src to dest.

    Example:

      # copy "main.c" to "build/main.c"
      sys.cp "main.c", "build/main.c"     # prints "cp main.c build/main.c"
    

    If dest is a directory, copy src to dest/src. If src is an array of strings or a filelist, copy all files listed in src to the directory dest.

    Examples:

      # copy "main.c" to the "build" directory
      sys.cp "main.c", "build"
    
      # copy all files ending in ".c" from the current directory to the
      # "build" directory
      sys.cp sys["*.c"], "build"
    

    Raises a SystemCallError if src is a directory or doesn’t exist.

  • cp_r(src, dest)

    Does the same as cp(src, dest), but also accepts a directory/directories as src. Directories are recursively copied to dest.

    Example:

      # Recursively copy all files/directories in the "src" directory
      # to the (existing) "/backup" directory.
      sys.cp_r sys["src/*"], "/backup"    # prints "cp -r <list of src/* files> /backup"
    
  • mv(src, dest)

    If src is a path (string), move the file src to dest.

    Example:

      # move "build/foo.exe" to "dist/foo.exe"
      sys.mv "build/foo.exe", "dist/foo.exe"      # prints "mv build/foo.exe dist/foo.exe"
    

    If dest is a directory, move src do dest/src. If src is an array of pathes or a filelist, move all entries of src to the directory dest.

    Example:

      # move all files ending in ".exe" from the "build" directory to
      # the "dist" directory
      sys.mv sys["build/*.exe"], "dist"
    

    src may also be a (empty or non-empty) directory. Of course a mixed array/filelist of "normal" files and directories is also allowed.

    Raises a SystemCallError if src is an array/filelist and dest is not a directory.

  • touch(file)

    file may be a single path to a file, an array of pathes or a filelist. Updates the modification time and the access time of all files. If a file doesn’t exist, creates an empty one with this name.

    Examples:

      # "main.c" is a file, update its modification time
      sys.touch "main.c"
    
      # "ts1" and "ts2" don't exist, create two empty files
      sys.touch ["ts1", "ts2"]
    
  • safe_ln(src, dest)

    This creates a hard link dest which points to the same file as src, on platforms that support hard links. Simply copies src to dest on other platforms.

    Example:

      # link or copy "main.c" to "package/main.c"
      sys.safe_ln "main.c", "package/main.c"
          # prints "ln main.c package/main.c" if a hard link is created
          # prints "cp main.c package/main.c" if is main.c is copied
    
  • ln(src, dest)

    Creates a hard link dest which points to the same file as src. If dest is a directory, creates the hard link dest/src.

    Example:

      # link "main.c" to "package/main.c"
      sys.ln "main.c", "package"      # prints "ln main.c package"
    

    Raises a SystemCallError if dest is a file or doesn’t exist.

    Note:Not all file systems and operating systems support hard links. On operating systems without support for hard links, a NotImplementedError exception is risen. If the operating system supports hard links, but the file system not, a SystemCallError is risen.
  • ln_f(src, dest)

    Same as ln(src, dest), but overwrites dest if dest is a file.

    Example:

      # link "main.c" to "package/main.c", overwriting any existing
      # "package/main.c" file
      sys.ln_f "main.c", "package"
    
      # ... equivalent to
      sys.ln_f "main.c", "package/main.c"
    
  • ln_s(src, dest)

    Creates a symbolic link dest which points to src. If dest is a directory, creates the symbolic link dest/src.

    Examples:

      # Create the symbolic link "NEWS" to the existing file "ChangeLog"
      sys.ln_s "ChangeLog", "NEWS"    # prints "ln -s ChangeLog NEWS"
    

    Raises a SystemCallError if dest is the name of an existing file or src doesn’t exist.

    Note:Not all file systems and operating systems support symbolic links. On operating systems without support for symbolic links, a NotImplementedError exception is risen. If the operating system supports symbolic links, but the file system not, a SystemCallError is risen.
  • ln_sf(src, dest)

    Same as ln_s(src, dest), but overwrites dest if dest exists.

    Example:

      # Create the symbolic link "NEWS" to the existing file
      # "ChangeLog", overwrite any existing "NEWS" file.
      sys.ln_s "ChangeLog", "NEWS"    # prints "ln -sf ChangeLog NEWS"
    
  • install(src, dest, options = {})

    Copy file src to dest if dest doesn’t exist or differs from src. Install src to dest/src if dest is a directory. If src is an array/filelist, installs each entry in src under the dest directory.

    Options is a hash which may contain the following keys:

    :mode:If given, after copying the mode of the target file(s) is changed to the integer given as value.
    :preserve:Takes either true or false. If given and true, the target file(s) will have the same access and modification times as the source file(s).

    Examples:

      # copy the file "./ruby" to "/usr/local/bin/ruby19" and change the
      # mode of the target file to 0755.
      sys.install "ruby", "/usr/local/bin/ruby19", :mode => 0755
    
      # install all files in the "lib" directory in "/usr/lib/foo" and
      # change the access and modification times of the target files to
      # match those of their source files.
      sys.install sys["lib/*"], "/usr/lib/foo", :preserve => true
    
  • chmod(mode, file)

    file may be a single file name or an array/filelist. Changes the file permissions of all given files to the bit pattern represented by the integer mode.

    Examples:

      # make file "/usr/local/bin/ruby" executable
      sys.chmod 0755, "/usr/local/bin/ruby"   # prints "chmod 0755 /usr/local/bin/ruby"
    
      # make all files in the "bin" directory executable
      sys.chmod 0755, sys["bin/*"]
    
    Note:Not all file systems/operating systems support the same permission bits. This method will only set the supported ones.
  • ruby(arg1, arg2, …)

    Starts a new ruby interpreter with the given arguments.

    Example:

      sys.ruby "setup.rb", "--prefix=/usr"    # prints "<absolute path to ruby> setup.rb --prefix=/usr"
    
    IMPORTANT:It does NOT start a subshell.

    Bad Example:

      # This probably does not do what was intended. Ruby will search
      # for the script file with the name "setup.rb --prefix=/usr"!
      sys.ruby "setup.rb --prefix=/usr"
    
    Note:Rant determines the absolute path to the ruby interpreter which is running the current Rant instance. It uses this path to start a new ruby interpreter. As a result, this method will also work when "ruby" is not on the PATH.
  • write_to_file(fn, text)

    Requires import "sys/more"

    Write the string text to the file with name fn. If the file already exists, it is overwritten, otherwise a new file is created.

    Example:

      import "sys/more"
    
      sys.write_to_file "version", "1.2.0\n"  # => prints "writing 6 bytes to file `version'"
    
  • write_to_binfile(fn, data)

    Requires import "sys/more"

    Like write_to_file(fn, data) but opens the file in binary mode.

    Example:

      import "sys/more"
    
      require "digest/md5"
      data = Digest::MD5.digest("some_string")
    
      sys.write_to_binfile "hash", data  # => prints "writing 16 bytes to file `hash'"
    
  • unpack_tgz(fn, options = {})

    Requires import "sys/tgz"

    Unpack the gzipped tar archive file with the file name fn in the current directory. If options contains the key :in, its value will be used as name of the output directory.

    Example:

      import "sys/tgz"
    
      # Creates the "pkg" directory if it doesn't exist and unpacks all
      # contents of "rant-0.4.6.tgz" in the "pkg" directory.
      sys.unpack_tgz "rant-0.4.6.tgz", :in => "pkg"
    

    Existing files will be overwritten.

  • unpack_zip(fn, options = {})

    Requires import "sys/zip"

    Unpack the zip archive file with the file name fn in the current directory. If options contains the key :in, its value will be used as name of the output directory.

    Example:

      import "sys/zip"
    
      # Creates the "pkg" directory if it doesn't exist and unpacks all
      # contents of "rant-0.4.6.zip" in the "pkg" directory.
      sys.unpack_zip "rant-0.4.6.zip", :in => "pkg"
    

    Existing files will be overwritten.

The following methods are "silent", i.e. they don’t print messages to standard output:

  • pwd

    Returns the current working directory as string.

    Example:

      sys.pwd             # => "/home/user"
    
  • compare_file(a, b)

    Returns true if the files a and b have the same contents, false otherwise.

    Example:

      unless sys.compare_file("lib/main.c", "/backup/main.c")
          puts "lib/main.c differs from /backup/main.c"
      end
    

    Raises a SystemCallError if a or b is not a file.

  • uptodate?(new, old_list)

    Returns true if the file with name new is newer (checked by file modification time) than all files listed in the old_list array/filelist. A non-existent file (including new) is considered older than any other file.

    Example:

      unless sys.uptodate?("foo.exe", sys["src/*.c", "include/*.h"])
          puts "(re)build of foo.exe required"
      end
    
  • expand_path(path)

    Resolves any "." or ".." elements in path and expands path to an absolute path. Replaces a leading @ character with an absolute path to the project’s root directory. Returns the resulting path string.

    Examples, assuming current directory is "/home/user/project/sub" and project root directory is "/home/user/project":

      sys.expand_path("README")           # => "/home/user/project/sub/README"
      sys.expand_path("./README")         # => "/home/user/project/sub/README"
      sys.expand_path("@README")          # => "/home/user/project/README"
      sys.expand_path("../../README")     # => "/home/user/README"
      sys.expand_path("/@README")         # => "/@README"
      sys.expand_path("subsub/./../")     # => "/home/user/project/sub"
    
  • split_all(path)

    Splits path into all its elements and returns and array.

    Examples:

      sys.split_all("abc")                # => ["abc"]
      sys.split_all("foo/bar")            # => ["foo", "bar"]
      sys.split_all("foo/bar/baz")        # => ["foo", "bar", "baz"]
    
  • escape(arg)

    Escapes all spaces in arg for the shell which is used on the current platform. Returns the escaped string.

    Example:

      sys.escape("foo bar")
          # gives on Windows: '"foo bar"'
          # other systems: 'foo\ bar'
    

    If arg is an array (or filelist) all elements are escaped and the resulting strings joined together, seperated by spaces.

    Example:

      sys.escape(["foo bar", "arg 2"])
          # gives on Windows: '"foo bar" "arg 2"'
          # other systems: 'foo\ bar arg\ 2'
    
    Note:Might escape more special shell characters in the future.
  • sp(path)

    Does the same as escape(path), but also replaces all slashes with backslashes on windows.

    Example:

      libdir = "/home/user/program files/d"
      sources = ["foo bar.d", "util.d"]
      sys "dmd #{sys.sp sources} -offoo -I#{sys.sp libdir}"
          # executes the command
          #   on windows: 'dmd "foo bar.d" util.d -offoo -I"/home/user/program files/d"'
          #   other systems: 'dmd foo\ bar.d util.d -offoo -I/home/user/program\ files/d'
    
  • regular_filename(path)

    Replaces all platform dependent filename separators with a slash, thus returning a platform independent filename.

    Examples:

      # on windows:
      sys.regular_filename('foo\bar')             # "foo/bar"
    
      # on all platforms:
      sys.regular_filename('foo//bar')            # "foo/bar"
    
  • glob(pattern1, pattern2, …)

    [pattern1, pattern2, …]

    Returns a filelist including the given patterns. For a discussion of filelists, read doc/sys_filelist.rdoc.

    Examples:

      # the following two are equivalent
      sys.glob("*.c", "*.h")
      sys["*.c", "*.h"]
    

    Filelists created with this method, ignore entries starting with a dot.

  • glob_all(pattern1, pattern2, …)

    Like glob(pattern1, pattern2, …), but the created filelist doesn’t ignore entries starting with a dot.

  • root_dir?(path)

    Returns true if the given path specifies the root directory on Linux/Unix, a drive followed by a slash or backslash on Windows.

    Examples:

      # on Linux/Unix:
      sys.root_dir?("/")              # true
      sys.root_dir?("/bin")           # false
      sys.root_dir?("bin")            # false
    
      # on Windows:
      sys.root_dir?("C:\\")           # true
      # (a reminder: a double backslash in a literal string is treated
      # as an escape sequence and converted to a single backslash by
      # ruby)
      sys.root_dir?("C:/")            # true
      sys.root_dir?("bin")            # false
    
  • absolute_path?(path)

    Returns true if the given path is an absolute path, false otherwise.

    Examples:

      # on all systems:
      sys.absolute_path?("/home/me/main.c")   # true
      sys.absolute_path?("main.c")            # false
    
      # on windows:
      sys.absolute_path?("C:\\Programs")      # true
      sys.absolute_path?("C:/Programs")      # true
    

See also

Rantfile basics:doc/rantfile.rdoc
Advanced Rantfiles:doc/advanced.rdoc
Rant Overview:README