2010-07-23 6 views
0

Je dois mettre à jour un seul champ dans un grand nombre d'enregistrements. Normalement, je voudrais juste exécuter une instruction de mise à jour SQL rapide à partir de la console et faire avec, mais c'est un utilitaire que les utilisateurs finaux doivent être en mesure de fonctionner dans cette application.Mise à jour d'un grand jeu d'enregistrements dans Rails

Donc, voici mon code:

users = User.find(:all, :select => 'id, flag') 
users.each do |u| 
    u.flag = false 
    u.save 
end 

Je crains que cela va juste prendre un certain temps que le nombre d'utilisateurs augmente (en cours assis à environ 35k, ajoutant 2-5k par semaine). Y a-t-il un moyen plus rapide de faire cela?

Merci!

Répondre

5

Si vous voulez vraiment mettre à jour tous les dossiers, le plus simple est d'utiliser #update_all:

User.update_all(:flag => false) 

Ceci est l'équivalent de:

UPDATE users SET flag = 'f' 

(Le SQL exact sera différent selon votre adaptateur)

La méthode #update_all également acceptable Conditions de ts:

User.update_all({:flag => false}, {:created_on => 3.weeks.ago .. 5.hours.ago}) 

En outre, #update_all peuvent être combinés avec des étendues nommées:

class User < ActiveRecord::Base 
    named_scope :inactive, lambda {{:conditions => {:last_login_at => 2.years.ago .. 2.weeks.ago}} 
end 

User.inactive.update_all(:flag => false) 
0

Vous pouvez utiliser la méthode execute d'ActiveRecord pour exécuter la mise à jour SQL. Quelque chose comme ceci:

ActiveRecord::Base.connection.execute('UPDATE users SET flag=0') 
Questions connexes