activerecord_views 0.1.4 → 0.1.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/active_record_views/database_tasks.rb +91 -0
- data/lib/active_record_views/railtie.rb +0 -4
- data/lib/active_record_views/version.rb +1 -1
- data/lib/active_record_views.rb +2 -0
- metadata +9 -77
- data/.gitignore +0 -8
- data/.rspec +0 -2
- data/.tool-versions +0 -1
- data/Appraisals +0 -15
- data/Gemfile +0 -3
- data/LICENSE.txt +0 -22
- data/Rakefile +0 -14
- data/activerecord_views.gemspec +0 -28
- data/gemfiles/rails5_2.gemfile +0 -7
- data/gemfiles/rails6_0.gemfile +0 -7
- data/gemfiles/rails6_1.gemfile +0 -7
- data/gemfiles/rails7_0.gemfile +0 -7
- data/lib/tasks/active_record_views.rake +0 -99
- data/spec/active_record_views_checksum_cache_spec.rb +0 -112
- data/spec/active_record_views_extension_spec.rb +0 -459
- data/spec/active_record_views_spec.rb +0 -344
- data/spec/internal/Rakefile +0 -24
- data/spec/internal/app/models/dependency_a.rb +0 -3
- data/spec/internal/app/models/dependency_b.rb +0 -3
- data/spec/internal/app/models/dependency_c.rb +0 -3
- data/spec/internal/app/models/erb_test_model.rb +0 -7
- data/spec/internal/app/models/erb_test_model.sql.erb +0 -1
- data/spec/internal/app/models/external_file_test_model.rb +0 -3
- data/spec/internal/app/models/external_file_test_model.sql +0 -1
- data/spec/internal/app/models/heredoc_test_model.rb +0 -5
- data/spec/internal/app/models/modified_a.rb +0 -3
- data/spec/internal/app/models/modified_b.rb +0 -3
- data/spec/internal/app/models/namespace/test_model.rb +0 -3
- data/spec/internal/app/models/namespace/test_model.sql +0 -1
- data/spec/internal/config/database.yml +0 -9
- data/spec/internal/config/routes.rb +0 -3
- data/spec/spec_helper.rb +0 -132
- data/spec/support/silence_warnings.rb +0 -6
- data/spec/tasks_spec.rb +0 -110
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 483aba6d404f5f766bf6cc234b8c2b8a6675b6a5302f260a362673e95c56d41c
|
|
4
|
+
data.tar.gz: d95085556edf79f561de0bd9adffdcac7b60ba0e68c8a497140c1584bd0c7e64
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 260b637a4b39f22777a9151af3fe4f3305a34dfefd3dfd8410952f2a2a6b3c3a5d9252acb95d7a0fda674469eaf8aa8824576beec0f032ece1b8ca8b3f518e6e
|
|
7
|
+
data.tar.gz: 69ffc4688582c19b51e842afd5969168da26beccafafd0703d660226b4c3cd3faa1bdf6e0d37206e67decb77725a4f6abb11554e315cac5806b7ce12d7a3a7ee
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
module ActiveRecordViews::DatabaseTasks
|
|
2
|
+
def migrate(*)
|
|
3
|
+
super
|
|
4
|
+
|
|
5
|
+
unless ActiveRecordViews::Extension.create_enabled
|
|
6
|
+
Rails.application.eager_load!
|
|
7
|
+
ActiveRecordViews::Extension.process_create_queue!
|
|
8
|
+
ActiveRecordViews.drop_unregistered_views!
|
|
9
|
+
end
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def dump_schema(db_config, format = ActiveRecord.respond_to?(:schema_format) ? ActiveRecord.schema_format : ActiveRecord::Base.schema_format, *args)
|
|
13
|
+
super
|
|
14
|
+
|
|
15
|
+
return unless format == :sql
|
|
16
|
+
|
|
17
|
+
connection = if respond_to?(:migration_connection)
|
|
18
|
+
migration_connection
|
|
19
|
+
else
|
|
20
|
+
ActiveRecord::Base.connection
|
|
21
|
+
end
|
|
22
|
+
return unless connection.data_source_exists?('active_record_views')
|
|
23
|
+
|
|
24
|
+
filename = case
|
|
25
|
+
when respond_to?(:schema_dump_path)
|
|
26
|
+
schema_dump_path(db_config, format)
|
|
27
|
+
when respond_to?(:dump_filename)
|
|
28
|
+
spec_name = args.first
|
|
29
|
+
dump_filename(spec_name || db_config.name, format)
|
|
30
|
+
else
|
|
31
|
+
raise 'unsupported ActiveRecord version'
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
adapter = case
|
|
35
|
+
when respond_to?(:database_adapter_for)
|
|
36
|
+
database_adapter_for(db_config)
|
|
37
|
+
when respond_to?(:class_for_adapter, true)
|
|
38
|
+
adapter_name = if db_config.respond_to?(:adapter)
|
|
39
|
+
db_config.adapter
|
|
40
|
+
else
|
|
41
|
+
db_config.fetch('adapter')
|
|
42
|
+
end
|
|
43
|
+
class_for_adapter(adapter_name).new(db_config)
|
|
44
|
+
else
|
|
45
|
+
raise 'unsupported ActiveRecord version'
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
database_name = if db_config.respond_to?(:database)
|
|
49
|
+
db_config.database
|
|
50
|
+
else
|
|
51
|
+
db_config.fetch('database')
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
active_record_views_dump = Tempfile.open(['active_record_views_dump', '.sql'])
|
|
55
|
+
adapter.send(:run_cmd, 'pg_dump', %W[--data-only --no-owner --table=active_record_views #{database_name} -f #{active_record_views_dump.path}], 'dumping')
|
|
56
|
+
adapter.send(:remove_sql_header_comments, active_record_views_dump.path)
|
|
57
|
+
|
|
58
|
+
active_record_views_dump_content = active_record_views_dump.read
|
|
59
|
+
|
|
60
|
+
# Substitute out any timestamps that were dumped from the active_record_views table
|
|
61
|
+
#
|
|
62
|
+
# Before:
|
|
63
|
+
#
|
|
64
|
+
# COPY public.active_record_views (name, class_name, checksum, options, refreshed_at) FROM stdin;
|
|
65
|
+
# test_view TestView 42364a017b73ef516a0eca9827e6fa00623257ee {"dependencies":[]} 2021-10-26 02:49:12.247494
|
|
66
|
+
# \.
|
|
67
|
+
#
|
|
68
|
+
# After:
|
|
69
|
+
#
|
|
70
|
+
# COPY public.active_record_views (name, class_name, checksum, options, refreshed_at) FROM stdin;
|
|
71
|
+
# test_view TestView 42364a017b73ef516a0eca9827e6fa00623257ee {"dependencies":[]} \N
|
|
72
|
+
# \.
|
|
73
|
+
if active_record_views_dump_content !~ /^COPY public.active_record_views \(.+, refreshed_at\) FROM stdin;$/
|
|
74
|
+
raise 'refreshed_at is not final column'
|
|
75
|
+
end
|
|
76
|
+
active_record_views_dump_content.gsub!(/\t\d\d\d\d-\d\d-\d\d.*$/, "\t\\N")
|
|
77
|
+
|
|
78
|
+
active_record_views_dump_content = active_record_views_dump_content
|
|
79
|
+
.lines
|
|
80
|
+
.chunk { |line| line.include?("\t") }
|
|
81
|
+
.flat_map { |is_data, lines| is_data ? lines.sort : lines }
|
|
82
|
+
.join
|
|
83
|
+
|
|
84
|
+
File.open filename, 'a' do |io|
|
|
85
|
+
io.puts active_record_views_dump_content
|
|
86
|
+
end
|
|
87
|
+
ensure
|
|
88
|
+
active_record_views_dump&.close
|
|
89
|
+
active_record_views_dump&.unlink
|
|
90
|
+
end
|
|
91
|
+
end
|
data/lib/active_record_views.rb
CHANGED
|
@@ -15,6 +15,8 @@ module ActiveRecordViews
|
|
|
15
15
|
def self.init!
|
|
16
16
|
require 'active_record_views/extension'
|
|
17
17
|
::ActiveRecord::Base.send :include, ActiveRecordViews::Extension
|
|
18
|
+
require 'active_record_views/database_tasks'
|
|
19
|
+
::ActiveRecord::Tasks::DatabaseTasks.singleton_class.prepend ActiveRecordViews::DatabaseTasks
|
|
18
20
|
require 'active_record_views/database_cleaner/truncation_extension' if defined? ::DatabaseCleaner
|
|
19
21
|
end
|
|
20
22
|
|
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: activerecord_views
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.1.
|
|
4
|
+
version: 0.1.6
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Jason Weathered
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: bin
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date:
|
|
11
|
+
date: 2023-11-06 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: activerecord
|
|
@@ -16,20 +16,20 @@ dependencies:
|
|
|
16
16
|
requirements:
|
|
17
17
|
- - ">="
|
|
18
18
|
- !ruby/object:Gem::Version
|
|
19
|
-
version: '
|
|
19
|
+
version: '6.0'
|
|
20
20
|
- - "<"
|
|
21
21
|
- !ruby/object:Gem::Version
|
|
22
|
-
version: '7.
|
|
22
|
+
version: '7.2'
|
|
23
23
|
type: :runtime
|
|
24
24
|
prerelease: false
|
|
25
25
|
version_requirements: !ruby/object:Gem::Requirement
|
|
26
26
|
requirements:
|
|
27
27
|
- - ">="
|
|
28
28
|
- !ruby/object:Gem::Version
|
|
29
|
-
version: '
|
|
29
|
+
version: '6.0'
|
|
30
30
|
- - "<"
|
|
31
31
|
- !ruby/object:Gem::Version
|
|
32
|
-
version: '7.
|
|
32
|
+
version: '7.2'
|
|
33
33
|
- !ruby/object:Gem::Dependency
|
|
34
34
|
name: appraisal
|
|
35
35
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -58,20 +58,6 @@ dependencies:
|
|
|
58
58
|
- - ">="
|
|
59
59
|
- !ruby/object:Gem::Version
|
|
60
60
|
version: '2.14'
|
|
61
|
-
- !ruby/object:Gem::Dependency
|
|
62
|
-
name: super_diff
|
|
63
|
-
requirement: !ruby/object:Gem::Requirement
|
|
64
|
-
requirements:
|
|
65
|
-
- - ">="
|
|
66
|
-
- !ruby/object:Gem::Version
|
|
67
|
-
version: '0'
|
|
68
|
-
type: :development
|
|
69
|
-
prerelease: false
|
|
70
|
-
version_requirements: !ruby/object:Gem::Requirement
|
|
71
|
-
requirements:
|
|
72
|
-
- - ">="
|
|
73
|
-
- !ruby/object:Gem::Version
|
|
74
|
-
version: '0'
|
|
75
61
|
- !ruby/object:Gem::Dependency
|
|
76
62
|
name: combustion
|
|
77
63
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -121,49 +107,16 @@ executables: []
|
|
|
121
107
|
extensions: []
|
|
122
108
|
extra_rdoc_files: []
|
|
123
109
|
files:
|
|
124
|
-
- ".gitignore"
|
|
125
|
-
- ".rspec"
|
|
126
|
-
- ".tool-versions"
|
|
127
|
-
- Appraisals
|
|
128
|
-
- Gemfile
|
|
129
|
-
- LICENSE.txt
|
|
130
110
|
- README.markdown
|
|
131
|
-
- Rakefile
|
|
132
|
-
- activerecord_views.gemspec
|
|
133
|
-
- gemfiles/rails5_2.gemfile
|
|
134
|
-
- gemfiles/rails6_0.gemfile
|
|
135
|
-
- gemfiles/rails6_1.gemfile
|
|
136
|
-
- gemfiles/rails7_0.gemfile
|
|
137
111
|
- lib/active_record_views.rb
|
|
138
112
|
- lib/active_record_views/checksum_cache.rb
|
|
139
113
|
- lib/active_record_views/database_cleaner/truncation_extension.rb
|
|
114
|
+
- lib/active_record_views/database_tasks.rb
|
|
140
115
|
- lib/active_record_views/extension.rb
|
|
141
116
|
- lib/active_record_views/railtie.rb
|
|
142
117
|
- lib/active_record_views/registered_view.rb
|
|
143
118
|
- lib/active_record_views/version.rb
|
|
144
119
|
- lib/activerecord_views.rb
|
|
145
|
-
- lib/tasks/active_record_views.rake
|
|
146
|
-
- spec/active_record_views_checksum_cache_spec.rb
|
|
147
|
-
- spec/active_record_views_extension_spec.rb
|
|
148
|
-
- spec/active_record_views_spec.rb
|
|
149
|
-
- spec/internal/Rakefile
|
|
150
|
-
- spec/internal/app/models/dependency_a.rb
|
|
151
|
-
- spec/internal/app/models/dependency_b.rb
|
|
152
|
-
- spec/internal/app/models/dependency_c.rb
|
|
153
|
-
- spec/internal/app/models/erb_test_model.rb
|
|
154
|
-
- spec/internal/app/models/erb_test_model.sql.erb
|
|
155
|
-
- spec/internal/app/models/external_file_test_model.rb
|
|
156
|
-
- spec/internal/app/models/external_file_test_model.sql
|
|
157
|
-
- spec/internal/app/models/heredoc_test_model.rb
|
|
158
|
-
- spec/internal/app/models/modified_a.rb
|
|
159
|
-
- spec/internal/app/models/modified_b.rb
|
|
160
|
-
- spec/internal/app/models/namespace/test_model.rb
|
|
161
|
-
- spec/internal/app/models/namespace/test_model.sql
|
|
162
|
-
- spec/internal/config/database.yml
|
|
163
|
-
- spec/internal/config/routes.rb
|
|
164
|
-
- spec/spec_helper.rb
|
|
165
|
-
- spec/support/silence_warnings.rb
|
|
166
|
-
- spec/tasks_spec.rb
|
|
167
120
|
homepage: http://github.com/jasoncodes/activerecord_views
|
|
168
121
|
licenses:
|
|
169
122
|
- MIT
|
|
@@ -183,29 +136,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
|
183
136
|
- !ruby/object:Gem::Version
|
|
184
137
|
version: '0'
|
|
185
138
|
requirements: []
|
|
186
|
-
rubygems_version: 3.
|
|
139
|
+
rubygems_version: 3.1.6
|
|
187
140
|
signing_key:
|
|
188
141
|
specification_version: 4
|
|
189
142
|
summary: Automatic database view creation for ActiveRecord
|
|
190
|
-
test_files:
|
|
191
|
-
- spec/active_record_views_checksum_cache_spec.rb
|
|
192
|
-
- spec/active_record_views_extension_spec.rb
|
|
193
|
-
- spec/active_record_views_spec.rb
|
|
194
|
-
- spec/internal/Rakefile
|
|
195
|
-
- spec/internal/app/models/dependency_a.rb
|
|
196
|
-
- spec/internal/app/models/dependency_b.rb
|
|
197
|
-
- spec/internal/app/models/dependency_c.rb
|
|
198
|
-
- spec/internal/app/models/erb_test_model.rb
|
|
199
|
-
- spec/internal/app/models/erb_test_model.sql.erb
|
|
200
|
-
- spec/internal/app/models/external_file_test_model.rb
|
|
201
|
-
- spec/internal/app/models/external_file_test_model.sql
|
|
202
|
-
- spec/internal/app/models/heredoc_test_model.rb
|
|
203
|
-
- spec/internal/app/models/modified_a.rb
|
|
204
|
-
- spec/internal/app/models/modified_b.rb
|
|
205
|
-
- spec/internal/app/models/namespace/test_model.rb
|
|
206
|
-
- spec/internal/app/models/namespace/test_model.sql
|
|
207
|
-
- spec/internal/config/database.yml
|
|
208
|
-
- spec/internal/config/routes.rb
|
|
209
|
-
- spec/spec_helper.rb
|
|
210
|
-
- spec/support/silence_warnings.rb
|
|
211
|
-
- spec/tasks_spec.rb
|
|
143
|
+
test_files: []
|
data/.gitignore
DELETED
data/.rspec
DELETED
data/.tool-versions
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
ruby 2.7.5
|
data/Appraisals
DELETED
data/Gemfile
DELETED
data/LICENSE.txt
DELETED
|
@@ -1,22 +0,0 @@
|
|
|
1
|
-
Copyright (c) 2012 Jason Weathered
|
|
2
|
-
|
|
3
|
-
MIT License
|
|
4
|
-
|
|
5
|
-
Permission is hereby granted, free of charge, to any person obtaining
|
|
6
|
-
a copy of this software and associated documentation files (the
|
|
7
|
-
"Software"), to deal in the Software without restriction, including
|
|
8
|
-
without limitation the rights to use, copy, modify, merge, publish,
|
|
9
|
-
distribute, sublicense, and/or sell copies of the Software, and to
|
|
10
|
-
permit persons to whom the Software is furnished to do so, subject to
|
|
11
|
-
the following conditions:
|
|
12
|
-
|
|
13
|
-
The above copyright notice and this permission notice shall be
|
|
14
|
-
included in all copies or substantial portions of the Software.
|
|
15
|
-
|
|
16
|
-
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
|
17
|
-
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
|
18
|
-
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
|
19
|
-
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
|
20
|
-
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
|
21
|
-
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
|
22
|
-
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/Rakefile
DELETED
|
@@ -1,14 +0,0 @@
|
|
|
1
|
-
require 'appraisal'
|
|
2
|
-
require 'bundler/setup'
|
|
3
|
-
require 'bundler/gem_tasks'
|
|
4
|
-
|
|
5
|
-
require 'rspec/core/rake_task'
|
|
6
|
-
RSpec::Core::RakeTask.new(:spec)
|
|
7
|
-
|
|
8
|
-
task :default do
|
|
9
|
-
if ENV['BUNDLE_GEMFILE'] == File.expand_path('Gemfile')
|
|
10
|
-
exec 'rake appraisal:all'
|
|
11
|
-
else
|
|
12
|
-
Rake::Task['spec'].invoke
|
|
13
|
-
end
|
|
14
|
-
end
|
data/activerecord_views.gemspec
DELETED
|
@@ -1,28 +0,0 @@
|
|
|
1
|
-
# -*- encoding: utf-8 -*-
|
|
2
|
-
lib = File.expand_path('../lib', __FILE__)
|
|
3
|
-
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
|
4
|
-
require 'active_record_views/version'
|
|
5
|
-
|
|
6
|
-
Gem::Specification.new do |gem|
|
|
7
|
-
gem.name = 'activerecord_views'
|
|
8
|
-
gem.version = ActiveRecordViews::VERSION
|
|
9
|
-
gem.authors = ['Jason Weathered']
|
|
10
|
-
gem.email = ['jason@jasoncodes.com']
|
|
11
|
-
gem.summary = %q{Automatic database view creation for ActiveRecord}
|
|
12
|
-
gem.homepage = 'http://github.com/jasoncodes/activerecord_views'
|
|
13
|
-
gem.license = 'MIT'
|
|
14
|
-
|
|
15
|
-
gem.files = `git ls-files`.split($/)
|
|
16
|
-
gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
|
|
17
|
-
gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
|
|
18
|
-
gem.require_paths = ['lib']
|
|
19
|
-
|
|
20
|
-
gem.add_dependency 'activerecord', ['>= 5.2', '< 7.1']
|
|
21
|
-
|
|
22
|
-
gem.add_development_dependency 'appraisal'
|
|
23
|
-
gem.add_development_dependency 'rspec-rails', '>= 2.14'
|
|
24
|
-
gem.add_development_dependency 'super_diff'
|
|
25
|
-
gem.add_development_dependency 'combustion', '>= 0.5.1'
|
|
26
|
-
gem.add_development_dependency 'pg'
|
|
27
|
-
gem.add_development_dependency 'warning'
|
|
28
|
-
end
|
data/gemfiles/rails5_2.gemfile
DELETED
data/gemfiles/rails6_0.gemfile
DELETED
data/gemfiles/rails6_1.gemfile
DELETED
data/gemfiles/rails7_0.gemfile
DELETED
|
@@ -1,99 +0,0 @@
|
|
|
1
|
-
Rake::Task['db:migrate'].enhance do
|
|
2
|
-
unless ActiveRecordViews::Extension.create_enabled
|
|
3
|
-
Rails.application.eager_load!
|
|
4
|
-
ActiveRecordViews::Extension.process_create_queue!
|
|
5
|
-
ActiveRecordViews.drop_unregistered_views!
|
|
6
|
-
end
|
|
7
|
-
end
|
|
8
|
-
|
|
9
|
-
schema_rake_task = Gem::Version.new(Rails.version) >= Gem::Version.new("6.1") ? 'db:schema:dump' : 'db:structure:dump'
|
|
10
|
-
|
|
11
|
-
Rake::Task[schema_rake_task].enhance do
|
|
12
|
-
table_exists = ActiveRecord::Base.connection.data_source_exists?('active_record_views')
|
|
13
|
-
|
|
14
|
-
if schema_rake_task == 'db:structure:dump'
|
|
15
|
-
ActiveRecord::Base.schema_format = :sql
|
|
16
|
-
end
|
|
17
|
-
|
|
18
|
-
schema_format = if ActiveRecord.respond_to?(:schema_format)
|
|
19
|
-
ActiveRecord.schema_format
|
|
20
|
-
else
|
|
21
|
-
ActiveRecord::Base.schema_format
|
|
22
|
-
end
|
|
23
|
-
|
|
24
|
-
if table_exists && schema_format == :sql
|
|
25
|
-
tasks = ActiveRecord::Tasks::DatabaseTasks
|
|
26
|
-
|
|
27
|
-
config = if ActiveRecord::Base.configurations.respond_to?(:configs_for)
|
|
28
|
-
if Rails.version.start_with?('6.0.')
|
|
29
|
-
ActiveRecord::Base.configurations.configs_for(env_name: Rails.env, spec_name: 'primary').config
|
|
30
|
-
else
|
|
31
|
-
ActiveRecord::Base.configurations.configs_for(env_name: Rails.env, name: 'primary')
|
|
32
|
-
end
|
|
33
|
-
else
|
|
34
|
-
tasks.current_config
|
|
35
|
-
end
|
|
36
|
-
adapter = if config.respond_to?(:adapter)
|
|
37
|
-
config.adapter
|
|
38
|
-
else
|
|
39
|
-
config.fetch('adapter')
|
|
40
|
-
end
|
|
41
|
-
database = if config.respond_to?(:database)
|
|
42
|
-
config.database
|
|
43
|
-
else
|
|
44
|
-
config.fetch('database')
|
|
45
|
-
end
|
|
46
|
-
|
|
47
|
-
filename = case
|
|
48
|
-
when tasks.respond_to?(:schema_dump_path)
|
|
49
|
-
tasks.schema_dump_path(config)
|
|
50
|
-
when tasks.respond_to?(:dump_filename)
|
|
51
|
-
tasks.dump_filename('primary')
|
|
52
|
-
else
|
|
53
|
-
tasks.schema_file
|
|
54
|
-
end
|
|
55
|
-
|
|
56
|
-
pg_tasks = tasks.send(:class_for_adapter, adapter).new(config)
|
|
57
|
-
psql_env = if pg_tasks.respond_to?(:psql_env, true)
|
|
58
|
-
pg_tasks.send(:psql_env)
|
|
59
|
-
else
|
|
60
|
-
pg_tasks.send(:set_psql_env)
|
|
61
|
-
{}
|
|
62
|
-
end
|
|
63
|
-
|
|
64
|
-
begin
|
|
65
|
-
active_record_views_dump = Tempfile.open("active_record_views_dump.sql")
|
|
66
|
-
require 'shellwords'
|
|
67
|
-
system(psql_env, "pg_dump --data-only --no-owner --table=active_record_views #{Shellwords.escape database} >> #{Shellwords.escape active_record_views_dump.path}")
|
|
68
|
-
raise 'active_record_views metadata dump failed' unless $?.success?
|
|
69
|
-
|
|
70
|
-
pg_tasks.send(:remove_sql_header_comments, active_record_views_dump.path)
|
|
71
|
-
|
|
72
|
-
# Substitute out any timestamps that were dumped from the active_record_views table
|
|
73
|
-
#
|
|
74
|
-
# Before:
|
|
75
|
-
#
|
|
76
|
-
# COPY public.active_record_views (name, class_name, checksum, options, refreshed_at) FROM stdin;
|
|
77
|
-
# test_view TestView 42364a017b73ef516a0eca9827e6fa00623257ee {"dependencies":[]} 2021-10-26 02:49:12.247494
|
|
78
|
-
# \.
|
|
79
|
-
#
|
|
80
|
-
# After:
|
|
81
|
-
#
|
|
82
|
-
# COPY public.active_record_views (name, class_name, checksum, options, refreshed_at) FROM stdin;
|
|
83
|
-
# test_view TestView 42364a017b73ef516a0eca9827e6fa00623257ee {"dependencies":[]} \N
|
|
84
|
-
# \.
|
|
85
|
-
active_record_views_dump_content = active_record_views_dump.read
|
|
86
|
-
if active_record_views_dump_content !~ /^COPY public.active_record_views \(.+, refreshed_at\) FROM stdin;$/
|
|
87
|
-
raise 'refreshed_at is not final column'
|
|
88
|
-
end
|
|
89
|
-
active_record_views_dump_content.gsub!(/\t\d\d\d\d-\d\d-\d\d.*$/, "\t\\N")
|
|
90
|
-
|
|
91
|
-
File.open filename, 'a' do |io|
|
|
92
|
-
io.puts active_record_views_dump_content
|
|
93
|
-
end
|
|
94
|
-
ensure
|
|
95
|
-
active_record_views_dump.close
|
|
96
|
-
active_record_views_dump.unlink
|
|
97
|
-
end
|
|
98
|
-
end
|
|
99
|
-
end
|
|
@@ -1,112 +0,0 @@
|
|
|
1
|
-
require 'spec_helper'
|
|
2
|
-
|
|
3
|
-
describe ActiveRecordViews::ChecksumCache do
|
|
4
|
-
let(:connection) { ActiveRecord::Base.connection }
|
|
5
|
-
|
|
6
|
-
describe 'initialisation' do
|
|
7
|
-
def metadata_table_exists?
|
|
8
|
-
connection.data_source_exists?('active_record_views')
|
|
9
|
-
end
|
|
10
|
-
|
|
11
|
-
context 'no existing table' do
|
|
12
|
-
it 'creates the table' do
|
|
13
|
-
expect(ActiveRecord::Base.connection).to receive(:execute).with(/\ACREATE TABLE active_record_views/).once.and_call_original
|
|
14
|
-
|
|
15
|
-
expect(metadata_table_exists?).to eq false
|
|
16
|
-
ActiveRecordViews::ChecksumCache.new(connection)
|
|
17
|
-
expect(metadata_table_exists?).to eq true
|
|
18
|
-
|
|
19
|
-
expect(connection.column_exists?('active_record_views', 'class_name')).to eq true
|
|
20
|
-
expect(connection.column_exists?('active_record_views', 'options')).to eq true
|
|
21
|
-
end
|
|
22
|
-
end
|
|
23
|
-
|
|
24
|
-
context 'existing table with current structure' do
|
|
25
|
-
before do
|
|
26
|
-
ActiveRecordViews::ChecksumCache.new(connection)
|
|
27
|
-
expect(metadata_table_exists?).to eq true
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
it 'does not recreate the table' do
|
|
31
|
-
expect(ActiveRecord::Base.connection).to receive(:execute).never
|
|
32
|
-
|
|
33
|
-
ActiveRecordViews::ChecksumCache.new(connection)
|
|
34
|
-
end
|
|
35
|
-
end
|
|
36
|
-
|
|
37
|
-
context 'existing table without class name' do
|
|
38
|
-
before do
|
|
39
|
-
connection.execute 'CREATE TABLE active_record_views(name text PRIMARY KEY, checksum text NOT NULL);'
|
|
40
|
-
|
|
41
|
-
connection.execute 'CREATE VIEW test_view AS SELECT 42 AS id;'
|
|
42
|
-
connection.execute "INSERT INTO active_record_views VALUES ('test_view', 'dummy');"
|
|
43
|
-
|
|
44
|
-
connection.execute 'CREATE VIEW other_view AS SELECT 123 AS id;'
|
|
45
|
-
end
|
|
46
|
-
|
|
47
|
-
it 'drops existing managed views recreates the table' do
|
|
48
|
-
expect(connection.column_exists?('active_record_views', 'class_name')).to eq false
|
|
49
|
-
expect(ActiveRecordViews.view_exists?(connection, 'test_view')).to eq true
|
|
50
|
-
expect(ActiveRecordViews.view_exists?(connection, 'other_view')).to eq true
|
|
51
|
-
|
|
52
|
-
sql_statements.clear
|
|
53
|
-
|
|
54
|
-
ActiveRecordViews::ChecksumCache.new(connection)
|
|
55
|
-
|
|
56
|
-
expect(sql_statements.grep_v(/^\s*SELECT/)).to match [
|
|
57
|
-
'BEGIN',
|
|
58
|
-
'DROP VIEW IF EXISTS test_view CASCADE;',
|
|
59
|
-
'DROP TABLE active_record_views;',
|
|
60
|
-
/^CREATE TABLE active_record_views/,
|
|
61
|
-
'COMMIT',
|
|
62
|
-
]
|
|
63
|
-
|
|
64
|
-
expect(connection.column_exists?('active_record_views', 'class_name')).to eq true
|
|
65
|
-
expect(ActiveRecordViews.view_exists?(connection, 'test_view')).to eq false
|
|
66
|
-
expect(ActiveRecordViews.view_exists?(connection, 'other_view')).to eq true
|
|
67
|
-
end
|
|
68
|
-
end
|
|
69
|
-
|
|
70
|
-
context 'existing table without options or refreshed at timestamp' do
|
|
71
|
-
before do
|
|
72
|
-
connection.execute 'CREATE TABLE active_record_views(name text PRIMARY KEY, class_name text NOT NULL UNIQUE, checksum text NOT NULL);'
|
|
73
|
-
|
|
74
|
-
connection.execute 'CREATE VIEW test_view AS SELECT 42 AS id;'
|
|
75
|
-
connection.execute "INSERT INTO active_record_views VALUES ('test_view', 'dummy', 'Dummy');"
|
|
76
|
-
end
|
|
77
|
-
|
|
78
|
-
it 'upgrades the table without losing data' do
|
|
79
|
-
expect(connection.column_exists?('active_record_views', 'options')).to eq false
|
|
80
|
-
expect(connection.column_exists?('active_record_views', 'refreshed_at')).to eq false
|
|
81
|
-
expect(ActiveRecordViews.view_exists?(connection, 'test_view')).to eq true
|
|
82
|
-
|
|
83
|
-
expect(ActiveRecord::Base.connection).to receive(:execute).with("ALTER TABLE active_record_views ADD COLUMN options json NOT NULL DEFAULT '{}';").once.and_call_original
|
|
84
|
-
expect(ActiveRecord::Base.connection).to receive(:execute).with("ALTER TABLE active_record_views ADD COLUMN refreshed_at timestamp;").once.and_call_original
|
|
85
|
-
|
|
86
|
-
ActiveRecordViews::ChecksumCache.new(connection)
|
|
87
|
-
|
|
88
|
-
expect(connection.column_exists?('active_record_views', 'options')).to eq true
|
|
89
|
-
expect(connection.column_exists?('active_record_views', 'refreshed_at')).to eq true
|
|
90
|
-
expect(ActiveRecordViews.view_exists?(connection, 'test_view')).to eq true
|
|
91
|
-
end
|
|
92
|
-
end
|
|
93
|
-
end
|
|
94
|
-
|
|
95
|
-
describe 'options serialization' do
|
|
96
|
-
let(:dummy_data) { {class_name: 'Test', checksum: '12345'} }
|
|
97
|
-
it 'errors if setting with non-symbol keys' do
|
|
98
|
-
cache = ActiveRecordViews::ChecksumCache.new(connection)
|
|
99
|
-
expect {
|
|
100
|
-
cache.set 'test', dummy_data.merge(options: {'blah' => 123})
|
|
101
|
-
}.to raise_error ArgumentError, 'option keys must be symbols'
|
|
102
|
-
end
|
|
103
|
-
|
|
104
|
-
it 'retrieves hash with symbolized keys and preserves value types' do
|
|
105
|
-
options = {foo: 'hi', bar: 123, baz: true}
|
|
106
|
-
|
|
107
|
-
cache = ActiveRecordViews::ChecksumCache.new(connection)
|
|
108
|
-
cache.set 'test', dummy_data.merge(options: options)
|
|
109
|
-
expect(cache.get('test')[:options]).to eq options
|
|
110
|
-
end
|
|
111
|
-
end
|
|
112
|
-
end
|