не могут обращаться к мутаторам ActiveRecord в блоке

Я внутри контроллера Rails, и я пытаюсь получить доступ к моей переменной экземпляра в блоке: Это дает ошибку, говоря, что «no method field1 для Nil»:

Prawn::Document.generate("hello.pdf") do
  @model.field1
end

Однако, если я это сделаю, тогда он работает:

my_model = @model
Prawn::Document.generate("hello.pdf") do
  my_model.field1
end

Может ли это иметь какое-то отношение к активаторам ActiveRecord или переменным экземпляра в блоке?

0
Спасибо, я думаю, что в этой теме есть лучшие ответы: P Я не думаю, что было бы разумно объединить эти два потока в один.
добавлено автор m33lky, источник
Этот вопрос также должен ответить на ваш вопрос: ruby block "> stackoverflow.com/questions/5150483/…
добавлено автор topek, источник

2 ответы

Эта проблема возникает, когда блок выполняется в другом контексте, обычно с помощью instance_eval . Итак, давайте проверим код:

#lib/prawn/document.rb: Document#initialize    
if block
  block.arity < 1 ? instance_eval(&block) : block[self]
end

Там у вас есть instance_eval , и вы также можете увидеть решение: передать блок, который принимает документ как аргумент, и теперь вы сможете получить доступ к переменным экземпляра, как обычно:

Prawn::Document.generate("hello.pdf") do |doc|
  @my_model.field1
end
3
добавлено

Это происходит потому, что код внутри блока выполняется в контексте объекта Prawn :: Document. Давайте перейдем внутрь этого кода:

module Prawn
  class Document
    def self.generate(filename,options={},&block)
      pdf = new(options,&block)
      pdf.render_file(filename)
    end

    def initialize(options={},&block)
      if block
        block.arity < 1 ? instance_eval(&block) : block[self]
      end
    end
  end
end

Как вы можете видеть, block выполняется с Document объектом как self . Он пытается найти @model в качестве переменной экземпляра self , не может этого сделать и вернуть nil . Если вы используете локальную переменную model , вы получаете помощь в закрытии и ваш код работает правильно

1
добавлено
Кроме того, есть ли короткий способ превратить переменную экземпляра в переменную в Ruby, не тратя ни на какую строку, как я сделал с my_model = @model ?
добавлено автор m33lky, источник
pro.ruby
pro.ruby
1 181 участник(ов)

Язык программирования Ruby Additional docs: https://rubyreferences.github.io/rubyref/ Invite: https://telegram.me/joinchat/Be4rsT2NuB3CyJaF26j1kA Кто хочет компилировать: @crystal_ru (его синтаксис основан на Ruby) Участник @proDOT

Ruby, Rails, Hanami | dry-rb
Ruby, Rails, Hanami | dry-rb
1 180 участник(ов)

https://telegram.me/rubyjob - Ruby Job По вопросам - @eugene_shved

Ruby School .us
Ruby School .us
1 045 участник(ов)

Чат-болталка для учеников руби-школы и не только. Правила: https://telegra.ph/Pravila-chata-Rubi-shkoly-03-13

Random Ruby Chat
Random Ruby Chat
589 участник(ов)

Правила публикации вакансий: https://t.me/codenamecrud/60865

Rubyata
Rubyata
333 участник(ов)

Коммюнити Ruby и Ruby On Rails Флуд не приветствуются. Вакансии можно публиковать только и ТОЛЬКО по пятницам с хештегом #вакансия.

Ruby Talks
Ruby Talks
236 участник(ов)

Национальная Флеймотека

RubyRush
RubyRush
189 участник(ов)

rubyrush.ru программирование для самых новичков

Rails Chat
Rails Chat
87 участник(ов)

You are welcome to discuss Ruby On Rails development process and other stuff