PostgreSQL
 sql >> Base de données >  >> RDS >> PostgreSQL

postgresql nextval générant des valeurs existantes

Il y a un reset_pk_sequences! méthode sur l'Adaptateur Postgres . Vous pouvez l'appeler et il le définira sur max(id) + 1, ce qui est probablement ce que vous voulez.

Dans certains projets, je reçois des données ETL assez souvent pour justifier une tâche de râteau pour le faire pour tous les modèles, ou pour un modèle spécifié. Voici la tâche - incluez-la dans un Rakefile ou dans le sien sous lib/tasks :

desc "Reset all sequences. Run after data imports"
task :reset_sequences, :model_class, :needs => :environment do |t, args|
  if args[:model_class]
    classes = Array(eval args[:model_class])
  else
    puts "using all defined active_record models"
    classes = []
    Dir.glob(RAILS_ROOT + '/app/models/**/*.rb').each { |file| require file }
    Object.subclasses_of(ActiveRecord::Base).select { |c|
      c.base_class == c}.sort_by(&:name).each do |klass|
        classes << klass
      end
  end
  classes.each do |klass|
      next if klass == CGI::Session::ActiveRecordStore::Session && ActionController::Base.session_store.to_s !~ /ActiveRecordStore/

        puts "reseting sequence on #{klass.table_name}"
        ActiveRecord::Base.connection.reset_pk_sequence!(klass.table_name)
    end
end

Vous pouvez maintenant l'exécuter pour tous les modèles (définis sous RAIS_ROOT/app/models) en utilisant rake reset_sequences , ou pour un modèle spécifique en transmettant un nom de classe.