Rails:如何在 rake 任务中定义函数

cqc*_*991 2 ruby rake ruby-on-rails

在我的任务文件中post.rake,我想重用一个函数

  def save_post(title, href, source)
    post = Post.new(title: title, url: href, source: source)
    if post.save
      puts title + 'saved'
    else
      puts title + 'not saved'
    end
  end
Run Code Online (Sandbox Code Playgroud)

但是,当我在这个文件中定义它并重新使用它时,它返回

NoMethodError: undefined method `save_post' for main:Object
Run Code Online (Sandbox Code Playgroud)

post.rake如下所示:

task :fetch_post => :environment do
  require 'nokogiri'
  require 'open-uri'

  url = 'http://example.com'
  doc = Nokogiri::HTML(open(url) )
  puts doc.css("title").text
  doc.css(".a").each do |item_info|
    title = item_info.text
    href = item_info['href']
    save_post(title, href)
  end

  def save_post(title, href)
    post = Post.new(title: title, url: href)
    if post.save
      puts title + 'saved'
    else
      puts title + 'not saved'
    end
  end
end
Run Code Online (Sandbox Code Playgroud)

内容抓取部分有效。我只是将保存后的代码移出,想将方法抽象出来。

我应该把def method?

Ser*_*sev 6

如果您在 rake 任务中定义方法,它们将成为全局可访问的,这可能会产生不希望的副作用。更简洁的方法是使用内联 lambda(或将方法移动到应用程序中的某个类)

task :fetch_post => :environment do
  require 'nokogiri'
  require 'open-uri'

  save_post = ->(title, href) {
    post = Post.new(title: title, url: href)
    if post.save
      puts title + 'saved'
    else
      puts title + 'not saved'
    end
  }

  url = 'http://example.com'
  doc = Nokogiri::HTML(open(url) )
  puts doc.css("title").text
  doc.css(".a").each do |item_info|
    title = item_info.text
    href = item_info['href']
    save_post.call(title, href)
  end

end
Run Code Online (Sandbox Code Playgroud)