From dcb52596942b047a342d08c3bd4578bc31fb9b1a Mon Sep 17 00:00:00 2001 From: Sven Fuchs Date: Sun, 22 Jun 2014 22:32:30 +0200 Subject: [PATCH] try fixing db setup for travis --- .travis.yml | 3 +- Rakefile | 99 ++++++++++++++++++++++++++++++++++++++++++++++------- 2 files changed, 87 insertions(+), 15 deletions(-) diff --git a/.travis.yml b/.travis.yml index 6a25506e..a624509a 100644 --- a/.travis.yml +++ b/.travis.yml @@ -8,8 +8,7 @@ rvm: addons: postgresql: 9.3 before_script: - # create 'logs' table matching 'travis-logs' - - 'RAILS_ENV=test bundle exec rake db:create db:structure:load mv_migrations db:migrate --trace' + - 'RAILS_ENV=test bundle exec rake db:create db:migrate --trace' notifications: irc: "irc.freenode.org#travis" diff --git a/Rakefile b/Rakefile index cc2ec531..866a2958 100644 --- a/Rakefile +++ b/Rakefile @@ -1,8 +1,9 @@ require 'bundler/setup' -CORE_PATH = Gem.loaded_specs['travis-core'].full_gem_path -ENV['DB_STRUCTURE'] = "#{CORE_PATH}/db/structure.sql" +require 'travis' +require 'travis/engine' begin + ENV['SCHEMA'] = File.expand_path('../db/schema.rb', $:.detect { |p| p.include?('travis-core') }) require 'micro_migrations' rescue LoadError # we can't load micro migrations on production @@ -17,17 +18,6 @@ rescue LoadError warn "could not load rspec" end -desc "move travis-core-specific migrations to db/migrate" -task 'mv_migrations' do - require 'fileutils' - migration_files = Dir["#{CORE_PATH}/spec/migrations/**/*.rb"] - migration_files.each do |f| - dest = 'db/migrate' - FileUtils.mkdir_p dest - FileUtils.cp f, dest - end -end - desc "generate gemspec" task 'travis-api.gemspec' do content = File.read 'travis-api.gemspec' @@ -52,3 +42,86 @@ task default: 'travis-api.gemspec' tasks_path = File.expand_path('../lib/tasks/*.rake', __FILE__) Dir.glob(tasks_path).each { |r| import r } + +module ActiveRecord + class Migration + class << self + attr_accessor :disable_ddl_transaction + end + + # Disable DDL transactions for this migration. + def self.disable_ddl_transaction! + @disable_ddl_transaction = true + end + + def disable_ddl_transaction # :nodoc: + self.class.disable_ddl_transaction + end + end + + class Migrator + def use_transaction?(migration) + !migration.disable_ddl_transaction && Base.connection.supports_ddl_transactions? + end + + def ddl_transaction(migration, &block) + if use_transaction?(migration) + Base.transaction { block.call } + else + block.call + end + end + + def migrate(&block) + current = migrations.detect { |m| m.version == current_version } + target = migrations.detect { |m| m.version == @target_version } + + if target.nil? && @target_version && @target_version > 0 + raise UnknownMigrationVersionError.new(@target_version) + end + + start = up? ? 0 : (migrations.index(current) || 0) + finish = migrations.index(target) || migrations.size - 1 + runnable = migrations[start..finish] + + # skip the last migration if we're headed down, but not ALL the way down + runnable.pop if down? && target + + ran = [] + runnable.each do |migration| + if block && !block.call(migration) + next + end + + Base.logger.info "Migrating to #{migration.name} (#{migration.version})" if Base.logger + + seen = migrated.include?(migration.version.to_i) + + # On our way up, we skip migrating the ones we've already migrated + next if up? && seen + + # On our way down, we skip reverting the ones we've never migrated + if down? && !seen + migration.announce 'never migrated, skipping'; migration.write + next + end + + begin + ddl_transaction(migration) do + migration.migrate(@direction) + record_version_state_after_migrating(migration.version) + end + ran << migration + rescue => e + canceled_msg = Base.connection.supports_ddl_transactions? ? "this and " : "" + raise StandardError, "An error has occurred, #{canceled_msg}all later migrations canceled:\n\n#{e}", e.backtrace + end + end + ran + end + end + + class MigrationProxy + delegate :disable_ddl_transaction, to: :migration + end +end