2015-04-10 2 views
0

Вот команда рубин Я хотел бы сохранить выход Time.now.strftime('%m%d%Y_%H%M') я думал, что я мог бы просто добавить что-то вроде этого, чтобы мой рецепт "инициализировать атрибут chef с блоком ruby?

TODAY={ ::Time.now.strftime('%m%d%Y_%H%M') } 

, но это не похоже на работу

==> default: [2015-04-10T17:53:44+00:00] ERROR: /tmp/vagrant-chef/eb36617d9c55f20fcee6cd316a379482/cookbooks/test-cookbook/recipes/install_app.rb:12: syntax error, unexpected '}', expecting tASSOC 
    ==> default: TODAY={ (Time.now.strftime('%m%d%Y_%H%M')) } 
    ==> default:           ^
    ==> default: [2015-04-10T17:53:44+00:00] FATAL: Chef::Exceptions::ChildConvergeError: Chef run process exited unsuccessfully (exit code 1) 

в конце концов, я хочу, чтобы сделать этот атрибут, чтобы я мог получить доступ к нему из нескольких рецептов

default['neustar-npac-deployment']['node_ohai_time'] = TODAY={ ::Time.now.strftime('%m%d%Y_%H%M') } 

спасибо!

+0

Почему у вас есть '{}' это не блок, а фактический синтаксис Hash. если вы хотите, чтобы это был ленивый блок, используйте '-> {}' или 'lambda {}', который будет генерировать 'lambda' или' Proc.new {} ', которые будут генерировать true' Proc'. что-то вроде 'TODAY = -> {Time.now.strftime ('% m% d% Y_% H% M')}'. Тогда для получения результата это будет 'TODAY.call', или вы можете просто установить его непосредственно как' TODAY = Time.now.strftime ('% m% d% Y_% H% M') ', но, похоже, вы этого хотели чтобы быть ленивым оцененным, поэтому лямбда может поместиться лучше всего. – engineersmnky

+0

Я не против, если он ленив, я просто следовал примеру, не понимая, для чего предназначены '{}'. Я попытаюсь использовать его непосредственно и посмотреть, не делает ли это трюк. Спасибо – david

+0

Моя точка была 'TODAY = Time.now.strftime ('% m% d% Y_% H% M')' означает 'СЕГОДНЯ' не изменится после его оценки, потому что это фиксированная константа, где как' TODAY = -> {Time.now.strftime ('% m% d% Y_% H% M')} 'означает, что каждый раз, когда вы используете' TODAY.call', он будет оценивать лямбда и возвращать текущий ответ. Имеет ли это смысл? – engineersmnky

ответ

2

По вашему запросу я отправляю это как ответ.

В данный момент вы используете {} неправильно, так как это не блок, а буква Hash, поэтому он жаловался. Чтобы сделать этот блок, вы должны использовать объект lambda или Proc.

лямбда

лямбда могут быть созданы с помощью одного из 2-х разных стилей синтаксиса

-> { "This is a lambda" } 
#=> #<Proc:[email protected](irb):1 (lambda)> 
lambda { "This is also a lambda" } 
#=> #<Proc:[email protected](irb):2 (lambda)> 

В любом случае это вполне приемлемо

Proc

Проки могут быть созданы с использованием Proc.new { "This is a proc" }

по этому вопросу семантические различия не нужны.

lambda и Proc будут ленивы оценивать утверждение внутри блока на #call, что означает, что значение может оставаться текучим.

Давайте возьмем ваш пример:

NOW = Time.now.strftime('%m%d%Y_%H%M') 
# in this case NOW will be evaluated once and will always equal the 
# string result of when it was first interpretted 
TODAY = -> {Time.now.strftime('%m%d%Y_%H%M')} 
# in this case TODAY is simply a lambda and it's value will be dependent 
# upon the time when you "call" it so something like this will clearly illustrate 
# the difference 
while NOW == TODAY.call 
    puts "Still the same time" 
end 
# after this NOW will still reflect it's initial set value and for 
# a while ~ 1 minute this will output "Still the same time" 
# at some point TODAY.call will increment up by 1 minute because it is 
# re-evaluated on each `#call` thus allowing it to change periodically with the clock 

Я надеюсь, что это каким-то образом поможет вам лучше понять эту концепцию.

+0

спасибо за отличное введение в прок и лямбда! – david

Смежные вопросы