Удалите старые записи на Heroku (Rails 3.1) с помощью граблей - PullRequest
2 голосов
/ 25 января 2012

Я не могу удалить старые записи из моего приложения на heroku.

В настоящее время работает планировщик heroku:

class Post < ActiveRecord::Base

def self.get_data
  # this populates my app but the database is starting to get large and I don't need the old records
  scr = Scrape.new
  data_array = scr.scrape
  store_data(data_array)
  # destroy_old_data
end

но я бы хотел раскомментировать вызов "destory_old_data".

def destroy_old_data
  # oldest = Post.where("updated_at > ?", 30.days.ago)
  # Post.delete_all("updated_at > ?", 30.days.ago)
  # Post.destroy_all("updated_at > ?", 30.days.ago)
  oldest = Post.find(:all, "updated_at > ?", 30.days.ago)
  oldest.destroy
end

Как видите, я попробовал несколько вещей, которые, кажется, работают локально в консоли, но я не могу заставить их работать на heroku.

Я получаю следующие ошибки:

ArgumentError: wrong number of arguments (2 for 1)

or

when using Post.find
NoMethodError: undefined method `destroy' for #<Array:0x00000004579898>

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

Буду признателен за любую помощь.

Ответы [ 3 ]

5 голосов
/ 26 января 2012

Чтобы обратиться к NoMethodError , вам нужно перебрать массив записей и вызвать destroy для каждой из них.

oldest.each { |r| r.destroy }

или вы можете использовать метод, подобный destroy_all, где вам даже не нужно делать дополнительные find. http://apidock.com/rails/ActiveRecord/Base/destroy_all/class

Post.destroy_all(['updated_at < ?', 30.days.ago])

Помещение условий в массив должно решить ArgumentError , как @ luke-chadwick, упомянутый в его ответе.

При этом следует учитывать, сколько записей вы удаляете (вот заметка из документации):

Примечание. Создание, обратный вызов и удаление каждой записи может занять много времени, если вы удаляете много записей одновременно. Он генерирует по крайней мере один запрос SQL DELETE для каждой записи (или, возможно, больше, для обеспечения ваших обратных вызовов). Если вы хотите быстро удалить много строк, не обращая внимания на их ассоциации или обратные вызовы, используйте вместо этого delete_all.

delete_all может быть более быстрым вариантом для вас, если вам не нужно очищать и другие связанные записи, такие как комментарии.

1 голос
/ 26 января 2012

Метод Post.destroy_all принимает все, что может быть передано параметру условий find (: all).Это включает в себя строку, хэш или массив.

Если вы покажете источник в документации для уничтожения всего, вы должны увидеть это:

# File activerecord/lib/active_record/base.rb, line 879
def destroy_all(conditions = nil)
  find(:all, :conditions => conditions).each { |object| object.destroy }
end

.видите, это требует одного аргумента.Поэтому условия должны быть заключены в фигурные скобки (как показано):

Post.destroy_all(['updated_at > ?', 30.days.ago])
1 голос
/ 26 января 2012

Вы пытаетесь «удалить» массив, список сообщений. Вместо этого вы должны вызвать удаление для каждого элемента в этом списке.

Post.where(["updated_at > ?", 30.days.ago]).each do |post|
  post.delete
end

Где, принимает один аргумент. И возвращает список сообщений, которые соответствуют его критериям. Затем вы можете зациклить эти сообщения и выполнить действие (delete) для каждого.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...