alterity 1.2.0 → 1.4.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 6283968b3d028f736da1517832ee5ebf8410aa4281aea4a2fa7af9e868a7ef89
4
- data.tar.gz: c4e6ae366bea0f1065aa303824c0f64f7dc684f7566e600ede7ece16c4e58b60
3
+ metadata.gz: 20a0079693908430f136c8f85839cdfa2a39872a4ec021a9014b5fd8bf27c493
4
+ data.tar.gz: 388fcc530f490f858e344eaf2a24e1287b275cae3b33739ced28b7a1a8a42d9f
5
5
  SHA512:
6
- metadata.gz: 1bf501f5c7f2ce204f995341c7ee2bf73a0c3d8fc16ed9b32ea710ff4b77251e464891df9866a6847b7740ae9472f1c639cae7b7ac31bb82381616b84d5ea66b
7
- data.tar.gz: 58fb3f6708f0b610d4129c960f1765e5073d74e0170f46456d549cf3f65ecf8e34da7b139efee3afbb5575d0f0c01d5630170590d51ffba2b6de9ef8d52e4a1c
6
+ metadata.gz: '095a935c8a09050ddfe41c0b149c167a9264d9f343260c06501717fe54fabd31cdb134634db009db13468efbe7f88ccff120889095e854edf2295f9523d15bc1'
7
+ data.tar.gz: 701b4b23a3478f4b8c3302371b41f5b70acbea0410e2dc5b5430ad88dd97f80926d211ea11f821cb43f4f33d6e66a14163e14fe7e94d85a3f9825d294b9b1fc1
data/lib/alterity.rb CHANGED
@@ -8,12 +8,14 @@ require "alterity/railtie"
8
8
  class Alterity
9
9
  class << self
10
10
  def process_sql_query(sql, &block)
11
+ return block.call if state.disabled
12
+
11
13
  case sql.tr("\n", " ").strip
12
14
  when /^alter\s+table\s+(?<table>.+?)\s+(?<updates>.+)/i
13
15
  table = $~[:table]
14
16
  updates = $~[:updates]
15
- if updates.split(",").all? { |s| s =~ /^\s*drop\s+foreign\s+key\s+\w+\s*$/i } ||
16
- updates.split(",").all? { |s| s =~ /^\s*add\s+constraint\s+`?\w+`?\s+foreign\s+key\s+\(`?\w+`?\)\s+references\s+`?\w+`?\s+\(`?\w+`?\)\s*$/i }
17
+ if updates.split(",").all? { |s| s =~ /^\s*drop\s+foreign\s+key/i } ||
18
+ updates.split(",").all? { |s| s =~ /^\s*add\s+constraint/i }
17
19
  block.call
18
20
  elsif updates =~ /drop\s+foreign\s+key/i || updates =~ /add\s+constraint/i
19
21
  # ADD CONSTRAINT / DROP FOREIGN KEY have to go to the original table,
@@ -35,6 +37,7 @@ class Alterity
35
37
 
36
38
  # hooks
37
39
  def before_running_migrations
40
+ require "open3"
38
41
  state.migrating = true
39
42
  set_database_config
40
43
  prepare_replicas_dsns_table
@@ -51,7 +54,21 @@ class Alterity
51
54
  alter_argument = %("#{updates.gsub('"', '\\"').gsub('`', '\\\`')}")
52
55
  prepared_command = config.command.call(altered_table, alter_argument).to_s.gsub(/\n/, "\\\n")
53
56
  puts "[Alterity] Will execute: #{prepared_command}"
54
- system(prepared_command) || raise("[Alterity] Command failed")
57
+ config.before_command&.call(prepared_command)
58
+
59
+ result_str = +""
60
+ exit_status = nil
61
+ Open3.popen2e(prepared_command) do |_stdin, stdout_and_stderr, wait_thr|
62
+ stdout_and_stderr.each do |line|
63
+ puts line
64
+ result_str << line
65
+ config.on_command_output&.call(line)
66
+ end
67
+ exit_status = wait_thr.value
68
+ config.after_command&.call(wait_thr.value.to_i)
69
+ end
70
+
71
+ raise("[Alterity] Command failed. Full output: #{result_str}") unless exit_status.success?
55
72
  end
56
73
 
57
74
  def set_database_config
@@ -4,7 +4,10 @@ class Alterity
4
4
  Configuration = Struct.new(
5
5
  :command,
6
6
  :host, :port, :database, :username, :password,
7
- :replicas_dsns_database, :replicas_dsns_table, :replicas_dsns
7
+ :replicas_dsns_database, :replicas_dsns_table, :replicas_dsns,
8
+ :before_command,
9
+ :on_command_output,
10
+ :after_command
8
11
  )
9
12
  CurrentState = Struct.new(:migrating, :disabled)
10
13
  cattr_accessor :state
@@ -36,10 +39,6 @@ class Alterity
36
39
  yield config
37
40
  end
38
41
 
39
- def command=(new_command)
40
- config.command = new_command
41
- end
42
-
43
42
  def disable
44
43
  state.disabled = true
45
44
  yield
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  class Alterity
4
- VERSION = "1.2.0"
4
+ VERSION = "1.4.1"
5
5
  end
@@ -10,7 +10,7 @@ RSpec.describe Alterity do
10
10
  ["CREATE UNIQUE INDEX `idx_users_on_col` ON `users` (col)", "`users`", "ADD UNIQUE INDEX `idx_users_on_col` (col)"],
11
11
  ["DROP INDEX `idx_users_on_col` ON `users`", "`users`", "DROP INDEX `idx_users_on_col`"],
12
12
  ["alter table users drop col", "users", "drop col"],
13
- [" ALTER TABLE\n users\n DROP col", "users", "DROP col"]
13
+ [" ALTER TABLE\n users\n DROP col", "users", "DROP col"],
14
14
  ].each do |(query, expected_table, expected_updates)|
15
15
  puts query.inspect
16
16
  expected_block = proc {}
@@ -32,7 +32,8 @@ RSpec.describe Alterity do
32
32
  "SHOW FULL FIELDS FROM `users`",
33
33
  "ALTER TABLE `installment_events` DROP FOREIGN KEY _fk_rails_0123456789",
34
34
  "ALTER TABLE `installment_events` DROP FOREIGN KEY _fk_rails_0123456789, DROP FOREIGN KEY _fk_rails_9876543210",
35
- "ALTER TABLE `installment_events` ADD CONSTRAINT `fk_rails_0cb5590091` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`)"
35
+ "ALTER TABLE `installment_events` ADD CONSTRAINT `fk_rails_0cb5590091` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`)",
36
+ "ALTER TABLE `installment_events` ADD CONSTRAINT `fk_rails_0cb5590091` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`) ON DELETE CASCADE",
36
37
  ].each do |query|
37
38
  expected_block = proc {}
38
39
  expect(expected_block).to receive(:call)
@@ -8,6 +8,7 @@ Alterity.configure do |config|
8
8
  system("echo '#{string}' > /tmp/custom_command_result.txt")
9
9
  system("echo '#{altered_table}' >> /tmp/custom_command_result.txt")
10
10
  system("echo '#{alter_argument}' >> /tmp/custom_command_result.txt")
11
+ "ls /"
11
12
  }
12
13
 
13
14
  config.replicas(
@@ -23,4 +24,16 @@ Alterity.configure do |config|
23
24
  "h=#{ENV['MYSQL_HOST']}"
24
25
  ]
25
26
  )
27
+
28
+ config.before_command = lambda do |command|
29
+ File.new("/tmp/before_command.txt", "w").syswrite(command)
30
+ end
31
+
32
+ config.on_command_output = lambda do |output|
33
+ File.new("/tmp/on_command_output.txt", "w+").syswrite(output)
34
+ end
35
+
36
+ config.after_command = lambda do |exit_status|
37
+ File.new("/tmp/after_command.txt", "w").syswrite(exit_status)
38
+ end
26
39
  end
@@ -0,0 +1,9 @@
1
+ # frozen_string_literal: true
2
+
3
+ class AddYetAnotherColorToShirts < ActiveRecord::Migration[6.1]
4
+ def up
5
+ Alterity.disable do
6
+ add_column :shirts, :color3, :string
7
+ end
8
+ end
9
+ end
@@ -69,3 +69,9 @@ ruby ../spec/bin/test_custom_config_result.rb
69
69
 
70
70
  # Also testing what's in replicas_dsns, also checking that master was detected and removed.
71
71
  bundle e rails runner 'res=ActiveRecord::Base.connection.execute("select dsn from percona.replicas_dsns").to_a.flatten;p(res); res == ["h=host1,P=3306", "h=host2,P=3306"] || exit(1)'
72
+
73
+ rm /tmp/custom_command_result.txt
74
+ cp ../spec/bin/disabled_migration.rb db/migrate/20210728182628_add_yet_another_color_to_shirts.rb
75
+ bundle e rails db:migrate --trace
76
+ bundle e rails runner 'Shirt.columns.map(&:name).include?("color3") || exit(1)'
77
+ ruby ../spec/bin/test_disabled_state.rb
@@ -15,6 +15,25 @@ puts result
15
15
  p result.chars.map(&:hex)
16
16
 
17
17
  if result != expected_result
18
- puts "=> mismatch"
18
+ puts "=> mismatched result"
19
+ exit(1)
20
+ end
21
+
22
+
23
+ result = File.read("/tmp/before_command.txt")
24
+ if result != "ls /"
25
+ puts "=> mismatched before_command"
26
+ exit(1)
27
+ end
28
+
29
+ result = File.read("/tmp/on_command_output.txt")
30
+ if !result.include?("var")
31
+ puts "=> mismatched on_command_output"
32
+ exit(1)
33
+ end
34
+
35
+ result = File.read("/tmp/after_command.txt")
36
+ if result.strip != "0"
37
+ puts "=> mismatched after_command"
19
38
  exit(1)
20
39
  end
@@ -0,0 +1,6 @@
1
+ # frozen_string_literal: true
2
+
3
+ if File.exist?("/tmp/custom_command_result.txt")
4
+ puts "=> disabled state does not work"
5
+ exit(1)
6
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: alterity
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.2.0
4
+ version: 1.4.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Chris Maximin
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-05-05 00:00:00.000000000 Z
11
+ date: 2021-07-28 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: mysql2
@@ -53,8 +53,10 @@ files:
53
53
  - lib/alterity/version.rb
54
54
  - spec/alterity_spec.rb
55
55
  - spec/bin/custom_config.rb
56
+ - spec/bin/disabled_migration.rb
56
57
  - spec/bin/rails_app_migration_test.sh
57
58
  - spec/bin/test_custom_config_result.rb
59
+ - spec/bin/test_disabled_state.rb
58
60
  - spec/spec_helper.rb
59
61
  homepage: https://github.com/gumroad/alterity
60
62
  licenses:
@@ -85,6 +87,8 @@ summary: Execute your ActiveRecord migrations with Percona's pt-online-schema-ch
85
87
  test_files:
86
88
  - spec/alterity_spec.rb
87
89
  - spec/bin/custom_config.rb
90
+ - spec/bin/disabled_migration.rb
88
91
  - spec/bin/rails_app_migration_test.sh
89
92
  - spec/bin/test_custom_config_result.rb
93
+ - spec/bin/test_disabled_state.rb
90
94
  - spec/spec_helper.rb