Работа с файловой системой в Ruby ч. 2: Класс Dir

июня 30, 2011  |  Published in Ruby, Основы  |  1 Comment

ruby File APIПродолжая серию о File IO API в Ruby, сегодня мы рассмотрим класс Dir.

Класс Dir

Основная направленность класса Dir — предоставить пользователю возможность запрашивания, обхода и фильтрации по директориям файловой системы. Данный клас предоставляет несколько базовых методов для создания и удаления директорий. Давайте рассмотрим этот его функционал в первую очередь.

Создание директорий

Вы можете создать новую директорию в вашей файловой системе просто передав желаемый путь к ней (полный или относительный) в качестве аргумента в метод Dir.mkdir. Этот метод вызовет ошибку Errno::EEXIST если такая директория уже существует, или SystemCallError если директория не может быть создана в следствии ограниченых прав доступа.

Все относительные пути (включая и те, что вы передаете в методы класса File) происходят из пути к текущей рабочей директории, доступ к кодорой можно получить через метод Dir.pwd (pwd — print work directory). Вы можете изменить рабочую директорию через метод Dir.chdir (chdir — change directory). Для упрощения прыгания между рабочими дииректориями вы можете передать блок кода в метод chdir и рабочая директория будет изменена после его выполнения.

Dir.pwd
>> "/home/marcos/code"
Dir.mkdir("test")
Dir.chdir("test") do
  Dir.pwd
  >> "/home/marcos/code/test"
  File.new("file.rb", "w")
end
Dir.pwd
>> "/home/marcos/code"

Удаление директории

Для удаления директории вам следует передать путь к ней в метод Dir.rmdir (rmdir — remove directory), этот метод также имеет синоним — метод unlink. Эти методы удаляют только пустые директории, если же удаляемая директория содержит что-нибудь, то будет вызвана ошибка SystemCallError. Вы можете получить более мощный инструмент работы с директориями используя класс FileUtils, который мы рассмотрим в следующей статье.

Обход содержимого директории

Класс Dir предоставляет два метода для обхода содержимого директорий, это методы Dir.entries и Dir.glob.

Dir#entries возвращает массив с именами всего содержимого директории, включая текущий путь («.»), родительскую директорию («..») и все скрытые файлы (в linux это все те, в начале имен которых стоит точка). Те же правила относятся и к методу each, который возвращает все содержимое и действует на основе методов из модуля Enumerable.

Метод #entries может вызывать раздражение если вы желаете работать только с файлами, как то продемонстрировано в следующем примере, где мы пытаемся (в очень хитроумный способ) удалить все файлы из определенной директории.

d = Dir.new("/home/marcos/code")
d.entries.each do |e|
  next if e =~ /^\./
  file = File.join(d.path, e)
  File.delete(file) if File.file?(file)
end

Гораздо более удобный способ обхода файлов в директории — использовать метод .glob, или очень похожий метод []. Эти методы принимают шаблон и возвращают массив с путями всех видимых файлов, которые соответствуют шаблону.

Шаблоны основаны на специальном кратком синтаксисе, где «*» представляет любое число групповых символов, «**» представляет все дочерние директории (их проверка производится рекурсивно) и «?» представляет один групповой символ.

"*"         #все файлы текущей директории
"help.*"    #все файлы с именем help и любым расширением
"*/**/*.rb" #все файлы с расширением rb, из текущей и вложенных директорий

С этой техникой наш маленький пример становися еще более кратким:

Dir["/home/marcos/code/*"].each { |f| File.delete(f) if File.file?(f) }

Метод Dir.glob также принимает флаги (в том числе операторы) для настройки поведения, как, например File::FNM_DOTMATCH который включает скрытые файлы в результат поиска.

Dir.glob("rakefile")
>> []
Dir.glob("rakefile", File::FNM_CASEFOLD)
>> ["/home/marcos/code/Rakefile"]

Оригинал статьи на английском:

Tags: , ,

Responses

  1. mearion says:

    июля 1, 2011 at 08:41 (#)

    проще сразу сделать перево всего

Leave a Response

Для подсветки кода используйте BB - коды: [language]...[/language], где language может быть: ruby, javascript, css, html.