Как читать INI-файл в ruby

Как читать / писать ini-файл в ruby. У меня есть ini-файл, который мне нужен

  1. читать
  2. изменить запись
  3. написать в другое место

Как бы я сделал это в ruby? Документации на это мрачно.

6 ответов


Я недавно использовал ruby-inifile. Может быть, это перебор по сравнению с простыми фрагментами здесь...


используйте драгоценный камень InIFile

как сказал @method, используйте ini файл камень. Существует также ini gem, но я не использовал его.

нашел документации немного более полезно, чем документации на который ссылается страница gem.

было не так много примеров, поэтому вот немного кода, чтобы вы начали:

Пример Настройки

во-первых, создать файл /tmp/desktop.ini С этим содержанием:

[Desktop Entry]
Version=1.0
Type=Application
Name=Foo Viewer
Comment=The best viewer for Foo objects available!
TryExec=fooview
Exec=fooview %F
Icon=fooview

убедитесь, что вы запустите gem install inifile из командной строки.

Пример Кода

создайте файл типа /tmp/ini-test.rb С этим содержанием:

require 'inifile'
require 'pp'

# read an existing file
file = IniFile.load('/tmp/desktop.ini')
data = file["Desktop Entry"]

#output one property
puts "here is one property:"
puts data["Name"]

# pretty print object
puts "here is the loaded file:"
pp file

# create a new ini file object
new_file = IniFile.new

# set properties
new_file["Desktop Entry"] = {
    "Type" => "Application",
    "Name" => 'test',
    "Exec" => 'command',
}

# pretty print object
puts "here is a object created with new:"
pp new_file

# set file path
new_file.filename = "/tmp/new_ini_file.ini"

# save file
new_file.write()
puts "the new object has been saved as a file to /tmp/new_ini_file.ini"

Пример Результатов

запуск этого файла с ruby /tmp/ini-test.rb должно получиться что-то вроде:

here is one property:
Foo Viewer

here is the loaded file:
{ this output hidden for brevity }

here is a object created with new:
#<IniFile:0x007feeec000770
 @comment=";#",
 @content=nil,
 @default="global",
 @encoding=nil,
 @escape=true,
 @filename=nil,
 @ini=
  {"Desktop Entry"=>
    {"Type"=>"Application",
     "Name"=>"test",
     "Exec"=>"command",
     "Icon"=>"icon_filename",
     "Comment"=>"comment"}},
 @param="=">

the new object has been saved as a file to /tmp/new_ini_file.ini

изменить по мере необходимости удовлетворить ваши потребности.


вот модуль для чтения и записи .ini-файлы с как можно меньшим изменением исходного файла (для файлов, которые читают людей и машины):

класс IniNode инициализация def (имя, значение=nil) @line_start = -1; @line_end = -1; @level = 0; @имя name; @value = значение; @ключи= {}; @keylist = []; @изменен = ложь; @deleted = false; конец attr_reader :уровень:line_start,:line_end,:название:значение:keylist,:ключи:измененных, удаленных attr_writer :уровень:line_start,:line_end,:название:значение:keylist,:ключи:изменен,:удалены

def to_str верните @name.to_s + ' = ' + @значение.to_s; конец

def to_s возвращает новое значение.to_s; конец def to_i возвращает новое значение.to_i конец def to_f возвращает новое значение.to_f; конец

def вставить(ключ, значение nil); return @keys[ключ]; конец

деф вставить(ключ, значение) возвращает false if (@keys.has_key?(ключевой)); узел = nil; if (value & & ((значение.class == IniNode) | | (значение.class == IniSection))) значение узла; еще если (@level

def [] =(клавиша, значение) РЦ = вставить(ключ, значение); @keys[ключ].value = значение; @keys[ключ].modified = true; @modified = true; конец

def удалить (клавиша) возвращает false, если (! @ключи.has_key?(ключевой)); @keys[ключ].удаленные = True; @modified = true; конец конец

класс IniSection

def to_str return ('['+ @name +']'); конец конец

перезагрузка def начинать входной файл.новое (@name, " r"); спасение поднимать; еще prevnode = узел = self; lineno = 0; вход.каждый do / line| @русло.push (линия); parsed_node = parse_line (строка, строка); if (parsed_node); if (parsed_node.class == IniSection) if (parsed_node != узел) prev_node = узел; node = parsed_node; вставить (узел.имя, узел); prev_node.line_end = lineno-1; конец еще узел.вставка(parsed_node.имя, parsed_node); конец конец lineno += 1; конец вход.близко;

  node.line_end = @line_end = lineno - 1;
end

конец

def parse_line(lineno, line) вернуть ноль, если (строка = ~ / ^\s * $/); возвращает ноль, если (строка = ~ / ^\s*#/); возвращает ноль, если (строка = ~ / ^\s*;/); если (строка =~ /^\s*[\s*(.+)\с.]*$/) rv = IniSection.Новый($1); кемпер.line_start = lineno; кемпер.уровень = @Уровень + 1; возвращение rv; elsif операторы (линии =~ /^\х(\С?.[^=\s])\s =\s*(\S?[^#;][^#;\s\n]).$/) rv = IniNode.new ($1, $2); кемпер.line_start = rv.line_end = lineno; кемпер.уровень = @Уровень + 2; возвращение rv; конец вернет nil; конец

def написать вставленный= {}; @keylist.каждый do / sect| sectnode = @ключи[раздел]; далее, если (!сектнод.modified / / sectnode.удаленный); if (sectnode.line_end [^=\s]\s =\s*\s?.+[^#; \s]) (\s*[#;].)$/) line = $1 + keynode.to_str + $3 + " \n"; еще line = линия.gsub (/^(\s)(\С?.[^=\s]\s =\s*\s?[^#;]+[^#;\n\s]) (.*)$/){ $ 1 + keynode.to_str + $3}; конец @lines[keynode.line_start] = линия; конец конец конец

begin
  file = File.new(@name, 'w');
rescue
  raise(IniFileExc, "Failed to open " + @name + " for writing: #{$!}", caller);
else
  cnt = -1;
  @lines.each do |line|
    cnt += 1;
    if (inserted.has_key?(cnt))
      inserted[cnt].each do |ins|
        file.puts(ins + "\n");
      end
    end
    next  if (deleted[cnt]);
    file.puts(line);
  end
  file.close;
end

конец конец

пример использования:


begin
  ini = IniFile.new('file.ini');
  ini['common']['param'] = 'value';
  ini['common'].delete('unused_param');
  ini.delete('unused_section');
  print "Valuable value: ", ini['common']['param'], "\n";
  ini.write;
rescue IniFileExc
  print "Oh, that's not good: ", $!, "\n";
end

надеюсь, что это помогает.


вот еще один вариант: http://rubygems.org/gems/ini


Если я правильно понял, то

outFile = File.new('out.ini', 'w')
File.open('in.ini', 'r') do |inFile|
  inFile.each_line do |line|
    # foo is the entry you want to change, baz is its new value.
    outFile.puts(line.sub(/foo=(.*)/, 'foo=baz'))
  end
end
outFile.close

обратите внимание, что при использовании File.open С блоком, файл будет автоматически закрыт, когда блок прекращает работу.


file = File.new("your.ini", "r")
  while (line = file.gets)
   puts "#{line}" #additionally make changes
  end
file.close