Как сделать числовое сравнение строк

Я написал тест serverspec, который предназначен для проверки того, что объем оперативной памяти на сервере больше или равен монтированию, указанному в файле свойств.

   describe command('perl -n -e "if (/MemTotal:\s+(\d+)/) { print \$1; last; }" /proc/meminfo') do
     its(:stdout){ should be >= "#{property['ram']}"}
    end

На тестируемой машине по команде выдает "7539944"

Если для свойства ram установлено значение «888», то тест завершается ошибкой, так как при сравнении строк «888» больше, чем «7539944».

Могу ли я каким-то образом провести числовое сравнение строкового типа в спецификации сервера?

Этот сеанс irb показывает, как, по моему мнению, ведет себя Ruby и как я хотел бы, чтобы он вел себя

$ irb
1.9.3-p484 :001 > prop="888"
 => "888" 
1.9.3-p484 :002 > command="7539944"
 => "7539944" 
1.9.3-p484 :003 > command > prop
 => false 
1.9.3-p484 :004 > command.to_i > prop.to_i
 => true 

Если я изменю описание на это

describe command('perl -n -e "if (/MemTotal:\s+(\d+)/) { print \$1; last; }" /proc/meminfo') do
 its(:stdout){ should be >= "#{property['ram']}".to_i}
end

я получаю эту ошибку

Failures:

      1) std Command "perl -n -e "if (/MemTotal:\s+(\d+)/) { print \$1; last; }" /proc/meminfo" stdout should be >= 888
         On host `foo.bar.org'
         Failure/Error: its(:stdout){ should be >= "#{property['ram']}".to_i}
         ArgumentError:
           comparison of String with 888 failed
           sudo -p 'Password: ' /bin/sh -c perl\ -n\ -e\ \"if\ \(/MemTotal:\\s\+\(\\d\+\)/\)\ \{\ print\ \\\$1\;\ last\;\ \}\"\ /proc/meminfo
           7539944
         Shared Example Group: "ram::init" called from ./spec/std/spec.rb:5
         # ./spec/shared/ram/init.rb:4:in `block (3 levels) in <top (required)>'

person Vorsprung    schedule 30.10.2015    source источник
comment
Я думаю, вы сами дали ответ: если вы хотите сравнить строки как целые числа, преобразуйте строки в целые числа с помощью .to_i.   -  person zwippie    schedule 30.10.2015
comment
should be >= property['ram'].to_i ; это работает?   -  person illusionist    schedule 30.10.2015
comment
Я не знаю, как преобразовать its(:stdout) в целое число или даже получить из него значение. >= property['ram'].to_i подходит для RHS, но выдает ошибку типа, так как LHS — это строка   -  person Vorsprung    schedule 30.10.2015


Ответы (1)


Этот инструмент работает поверх старого доброго rspec. Для выполнения этой задачи DSL не требуется:

context 'memory' do
  it "should be greater than #{888}" do
    expect(`cat /proc/meminfo`[/MemTotal:\s+(\d+)/, 1].to_i).to be >= 888 
  end 
end

Вызов Perl из ruby ​​сделал мой день, кстати.

UPD Я немного поигрался с serverspec и не смог найти прямой реализации вашего требования. Следовательно, я бы посоветовал вам изменить String следующим образом:

class String
  def greater_than? other
    to_i > other.to_i rescue false
  end
end

Таким образом, вы сможете написать в своем сценарии:

its(:stdout) { should be_greater_than "#{property['ram']}" }

Надеюсь, поможет.

person Aleksei Matiushkin    schedule 30.10.2015
comment
не уверен, что могу использовать такие обратные кавычки в спецификации сервера. Тип command упакован и запускается через ssh на удаленном компьютере. ssh контролируется serverspec. Рад, что перл понравился :) - person Vorsprung; 30.10.2015
comment
спасибо! это работает, и мне это нравится. Конечно, я также нашел другое решение. Использование синтаксиса expect вместо should expect(subject.stdout.to_i).to be >= "#{property['ram']}".to_i действительно работает. Не удалось решить, как это сделать с должен - person Vorsprung; 30.10.2015
comment
Сомневаюсь, что у вас получится, поэтому синтаксис should был изменен на expect в современных rspec. - person Aleksei Matiushkin; 30.10.2015