mv-postgresql 1.0.1 → 2.0.0

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.
Files changed (29) hide show
  1. checksums.yaml +4 -4
  2. data/{README.rdoc → README.md} +69 -24
  3. data/lib/mv-postgresql.rb +68 -1
  4. data/lib/mv/postgresql/active_record/connection_adapters/postgresql_adapter_decorator.rb +11 -0
  5. data/lib/mv/postgresql/constraint/builder/check.rb +45 -0
  6. data/lib/mv/postgresql/constraint/builder/trigger.rb +69 -0
  7. data/lib/mv/postgresql/constraint/check.rb +11 -0
  8. data/lib/mv/postgresql/railtie.rb +11 -0
  9. data/lib/mv/postgresql/route/check.rb +17 -0
  10. data/lib/mv/postgresql/validation/absence.rb +11 -0
  11. data/lib/mv/postgresql/validation/builder/exclusion.rb +18 -0
  12. data/lib/mv/postgresql/validation/builder/format.rb +34 -0
  13. data/lib/mv/postgresql/validation/builder/inclusion.rb +18 -0
  14. data/lib/mv/postgresql/validation/builder/trigger/absence.rb +15 -0
  15. data/lib/mv/postgresql/validation/builder/trigger/exclusion.rb +16 -0
  16. data/lib/mv/postgresql/validation/builder/trigger/format.rb +16 -0
  17. data/lib/mv/postgresql/validation/builder/trigger/inclusion.rb +16 -0
  18. data/lib/mv/postgresql/validation/builder/trigger/length.rb +15 -0
  19. data/lib/mv/postgresql/validation/builder/trigger/presence.rb +15 -0
  20. data/lib/mv/postgresql/validation/builder/trigger/trigger_column.rb +17 -0
  21. data/lib/mv/postgresql/validation/builder/trigger/uniqueness.rb +15 -0
  22. data/lib/mv/postgresql/validation/check_support.rb +44 -0
  23. data/lib/mv/postgresql/validation/exclusion.rb +11 -0
  24. data/lib/mv/postgresql/validation/format.rb +25 -0
  25. data/lib/mv/postgresql/validation/inclusion.rb +11 -0
  26. data/lib/mv/postgresql/validation/length.rb +11 -0
  27. data/lib/mv/postgresql/validation/presence.rb +11 -0
  28. metadata +101 -8
  29. data/lib/migration_validators/adapters/postgresql.rb +0 -146
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 13c089d60aae49617aa26da0fe977a1908b03e3c
4
- data.tar.gz: 08cc2f9ed8b940c4075f78db5af52459b81800bd
3
+ metadata.gz: 6193f8d0d4867e6732ce747329a8779eb32778b1
4
+ data.tar.gz: d21b9c03169d1aa29db9c528d670f2676cdeac7a
5
5
  SHA512:
6
- metadata.gz: b14170815495b1c873fde107ad3a441e967b78c815e46c9ec49848152373da3f0c56b994ca96d7bce6494c13088888eac6a1566f52eb2c5c3fe31e1f2d51fcfe
7
- data.tar.gz: c08a261687f1d624d7d690737dfee64175a960e5abc693261c593ac39f4acceec48b87e8501d6acade946bffcd91b45065c4d554402fa3a1ea35b5fc885320ca
6
+ metadata.gz: 1895ba7e873687b119e4623366e9c9f089c1e75e39ad1b8eb4dd19b54324369e6973d50498d35d03fa8bd2b3cd7f64f37e1145be9094db96839f95bdc5058872
7
+ data.tar.gz: 270ede9167f1321282eb28028f5a3dd7d84562305fa8ba82ce19e15662d8e9a1a52a37fd0f16e534164b41ef0c01a5fc0cb5639a5ddf3a5cde154ad908774c25
@@ -1,9 +1,12 @@
1
+ [![Bitdeli Badge](https://d2weczhvl823v0.cloudfront.net/vprokopchuk256/mv-postgresql/trend.png)](https://bitdeli.com/free "Bitdeli Badge")
2
+ [![Build Status](https://travis-ci.org/vprokopchuk256/mv-postgresql.svg?branch=master)](https://travis-ci.org/vprokopchuk256/mv-postgresql)
3
+ [![Coverage Status](https://coveralls.io/repos/vprokopchuk256/mv-postgresql/badge.png?branch=master)](https://coveralls.io/r/vprokopchuk256/mv-postgresql?branch=master)
4
+ [![Gem Version](https://badge.fury.io/rb/mv-postgresql.svg)](http://badge.fury.io/rb/mv-postgresql)
5
+
1
6
  # Introduction
2
7
 
3
8
  mv-postgresql is the PostgreSQL driver for Migration Validators project (details here: https://github.com/vprokopchuk256/mv-core)
4
9
 
5
- # Validators
6
-
7
10
  ### uniqueness
8
11
 
9
12
  Examples:
@@ -11,20 +14,20 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
11
14
  validate uniqueness of the column 'column_name':
12
15
 
13
16
  ```ruby
14
- validate_column :table_name, :column_name, uniqueness: true
17
+ validates :table_name, :column_name, uniqueness: true
15
18
  ```
16
19
 
17
20
  define validation as trigger with specified failure message:
18
21
 
19
22
  ```ruby
20
- validate_column :table_name, :column_name,
23
+ validates :table_name, :column_name,
21
24
  uniqueness: { message: 'Error message', as: :trigger }
22
25
  ```
23
26
 
24
27
  define validation as unique index:
25
28
 
26
29
  ```ruby
27
- validate_column :table_name, :column_name, uniqueness: { as: :index }
30
+ validates :table_name, :column_name, uniqueness: { as: :index }
28
31
  ```
29
32
 
30
33
  all above are available in a create and change table blocks:
@@ -57,7 +60,7 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
57
60
  Examples:
58
61
 
59
62
  ```ruby
60
- validate_column :table_name, :column_name,
63
+ validates :table_name, :column_name,
61
64
  length: { in: 5..8,
62
65
  message: 'Wrong length message'}
63
66
  ```
@@ -65,14 +68,14 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
65
68
  allow `NULL`:
66
69
 
67
70
  ```ruby
68
- validate_column :table_name, :column_name,
71
+ validates :table_name, :column_name,
69
72
  length: { is: 3, allow_nil: true}
70
73
  ```
71
74
 
72
75
  allow blank values:
73
76
 
74
77
  ```ruby
75
- validate_column :table_name, :column_name,
78
+ validates :table_name, :column_name,
76
79
  length: { maximum: 3,
77
80
  too_long: 'Value is longer than 3 symbols' }
78
81
  ```
@@ -80,7 +83,7 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
80
83
  define constraint in trigger:
81
84
 
82
85
  ```ruby
83
- validate_column :table_name, :column_name,
86
+ validates :table_name, :column_name,
84
87
  length: { maximum: 3,
85
88
  as: :trigger,
86
89
  too_long: 'Value is longer than 3 symbols' }
@@ -110,13 +113,13 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
110
113
  valid values array:
111
114
 
112
115
  ```ruby
113
- validate_column :table_name, :column_name, inclusion: { in: [1, 2, 3] }
116
+ validates :table_name, :column_name, inclusion: { in: [1, 2, 3] }
114
117
  ```
115
118
 
116
119
  with failure message specified:
117
120
 
118
121
  ```ruby
119
- validate_column :table_name, :column_name,
122
+ validates :table_name, :column_name,
120
123
  inclusion: { in: [1, 2, 3],
121
124
  message: "Column 'column_name' should be equal to 1 or 2 or 3" }
122
125
  ```
@@ -124,7 +127,7 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
124
127
  make it as check constraint:
125
128
 
126
129
  ```ruby
127
- validate_column :table_name, :column_name,
130
+ validates :table_name, :column_name,
128
131
  inclusion: { in: [1, 2, 3],
129
132
  on: :update,
130
133
  as: :check }
@@ -133,7 +136,7 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
133
136
  make it in trigger:
134
137
 
135
138
  ```ruby
136
- validate_column :table_name, :column_name,
139
+ validates :table_name, :column_name,
137
140
  inclusion: { in: 1..3,
138
141
  on: :create,
139
142
  as: :trigger }
@@ -158,13 +161,13 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
158
161
  exclude 1, 2, and 3:
159
162
 
160
163
  ```ruby
161
- validate_column :table_name, :column_name, exclusion: { in: [1, 2, 3] }
164
+ validates :table_name, :column_name, exclusion: { in: [1, 2, 3] }
162
165
  ```
163
166
 
164
167
  the same with failure message:
165
168
 
166
169
  ```ruby
167
- validate_column :table_name, :column_name,
170
+ validates :table_name, :column_name,
168
171
  exclusion: {
169
172
  in: [1, 2, 3],
170
173
  message: "Column 'column_name' should not be equal to 1 or 2 or 3" }
@@ -173,7 +176,7 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
173
176
  as check constraint:
174
177
 
175
178
  ```ruby
176
- validate_column :table_name, :column_name,
179
+ validates :table_name, :column_name,
177
180
  exclusion: { in: [1, 2, 3],
178
181
  on: :update,
179
182
  as: :check }
@@ -182,7 +185,7 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
182
185
  as trigger:
183
186
 
184
187
  ```ruby
185
- validate_column :table_name, :column_name,
188
+ validates :table_name, :column_name,
186
189
  exclusion: { in: 1..3,
187
190
  on: :create,
188
191
  as: :trigger }
@@ -205,20 +208,20 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
205
208
  Examples:
206
209
 
207
210
  ```ruby
208
- validate_column :table_name, :column_name, presence: true
211
+ validates :table_name, :column_name, presence: true
209
212
  ```
210
213
 
211
214
  with failure message:
212
215
 
213
216
  ```ruby
214
- validate_column :table_name, :column_name,
217
+ validates :table_name, :column_name,
215
218
  presence: { message: 'value should not be empty' }
216
219
  ```
217
220
 
218
221
  implemented as trigger:
219
222
 
220
223
  ```ruby
221
- validate_column :table_name, :column_name,
224
+ validates :table_name, :column_name,
222
225
  presence: { message: 'value should not be empty',
223
226
  as: :trigger }
224
227
  ```
@@ -226,7 +229,7 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
226
229
  check when record is inserted only:
227
230
 
228
231
  ```ruby
229
- validate_column :table_name, :column_name,
232
+ validates :table_name, :column_name,
230
233
  presence: { message: 'value should not be empty',
231
234
  as: :trigger,
232
235
  on: :create }
@@ -242,6 +245,48 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
242
245
  * `allow_blank` - ignore validation for blank values. Default value: `false`
243
246
  * `as` - defines the way how constraint will be implemented. Possible values: `[:trigger, :check]` Default value: `:check`
244
247
 
248
+ ### absence
249
+
250
+ Examples:
251
+
252
+ ```ruby
253
+ validates :table_name, :column_name, absence: true
254
+ ```
255
+
256
+ with failure message:
257
+
258
+ ```ruby
259
+ validates :table_name, :column_name,
260
+ absence: { message: 'value should be empty' }
261
+ ```
262
+
263
+ implemented as trigger:
264
+
265
+ ```ruby
266
+ validates :table_name, :column_name,
267
+ absence: { message: 'value should be empty',
268
+ as: :trigger }
269
+ ```
270
+
271
+ check when record is inserted only:
272
+
273
+ ```ruby
274
+ validates :table_name, :column_name,
275
+ absence: { message: 'value should be empty',
276
+ as: :trigger,
277
+ on: :create }
278
+ ```
279
+
280
+ Options:
281
+
282
+ * `message` - message that should be shown if validation failed
283
+ * `on` - validation event. Possible values `[:save, :update, :create]`. Ignored unless `:as == :trigger`. Default value: `:save`
284
+ * `create_tigger_name` - Name of the 'before insert' trigger that will be created if `:as == :trigger` && `:on` in `[:save, :create]`
285
+ * `update_tigger_name` - Name of the 'before update' trigger that will be created if `:as == :trigger` && `:on` in `[:save, :update]`
286
+ * `allow_nil` - ignore validation for `nil` values. Default value: `false`
287
+ * `allow_blank` - ignore validation for blank values. Default value: `false`
288
+ * `as` - defines the way how constraint will be implemented. Possible values: `[:trigger, :check]` Default value: `:check`
289
+
245
290
  ### format
246
291
 
247
292
  Examples:
@@ -249,13 +294,13 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
249
294
  allows only values that contains 'word' inside:
250
295
 
251
296
  ```ruby
252
- validate_column :table_name, :column_name, format: { with: /word/ }
297
+ validates :table_name, :column_name, format: { with: /word/ }
253
298
  ```
254
299
 
255
300
  with failure message:
256
301
 
257
302
  ```ruby
258
- validate_column :table_name, :column_name,
303
+ validates :table_name, :column_name,
259
304
  format: { with: /word/,
260
305
  message: 'Column_name value should contain start word' }
261
306
  ```
@@ -263,7 +308,7 @@ mv-postgresql is the PostgreSQL driver for Migration Validators project (details
263
308
  implemented as trigger:
264
309
 
265
310
  ```ruby
266
- validate_column :table_name, :column_name,
311
+ validates :table_name, :column_name,
267
312
  format: { with: /word/,
268
313
  message: 'Column_name value should contain start word',
269
314
  as: :trigger }
@@ -1,4 +1,71 @@
1
1
  require 'mv-core'
2
+ require 'mv/postgresql/railtie'
2
3
 
3
- require File.expand_path(File.dirname(__FILE__)) + '/migration_validators/adapters/postgresql'
4
+ require 'mv/postgresql/route/check'
5
+
6
+ require 'mv/postgresql/constraint/check'
7
+
8
+ require 'mv/postgresql/constraint/builder/trigger'
9
+ require 'mv/postgresql/constraint/builder/check'
10
+
11
+ require 'mv/postgresql/validation/exclusion'
12
+ require 'mv/postgresql/validation/format'
13
+ require 'mv/postgresql/validation/inclusion'
14
+ require 'mv/postgresql/validation/length'
15
+ require 'mv/postgresql/validation/presence'
16
+ require 'mv/postgresql/validation/absence'
17
+
18
+ require 'mv/postgresql/validation/builder/trigger/exclusion'
19
+ require 'mv/postgresql/validation/builder/trigger/inclusion'
20
+ require 'mv/postgresql/validation/builder/trigger/length'
21
+ require 'mv/postgresql/validation/builder/trigger/format'
22
+ require 'mv/postgresql/validation/builder/trigger/presence'
23
+ require 'mv/postgresql/validation/builder/trigger/absence'
24
+ require 'mv/postgresql/validation/builder/trigger/uniqueness'
25
+
26
+ ActiveSupport.on_load(:mv_core) do
27
+ #router
28
+ Mv::Core::Router.define_route(:check, Mv::Postgresql::Route::Check)
29
+
30
+ #constraints
31
+ Mv::Core::Constraint::Factory.register_constraint(:check, Mv::Postgresql::Constraint::Check)
32
+
33
+ #constraint builders
34
+ Mv::Core::Constraint::Builder::Factory.register_builders(
35
+ Mv::Core::Constraint::Trigger => Mv::Postgresql::Constraint::Builder::Trigger,
36
+ Mv::Postgresql::Constraint::Check => Mv::Postgresql::Constraint::Builder::Check
37
+ )
38
+
39
+ #validations
40
+ Mv::Core::Validation::Factory.register_validations(
41
+ :exclusion => Mv::Postgresql::Validation::Exclusion,
42
+ :format => Mv::Postgresql::Validation::Format,
43
+ :inclusion => Mv::Postgresql::Validation::Inclusion,
44
+ :length => Mv::Postgresql::Validation::Length,
45
+ :presence => Mv::Postgresql::Validation::Presence,
46
+ :absence => Mv::Postgresql::Validation::Absence
47
+ )
48
+
49
+ #validation builders in trigger
50
+ Mv::Postgresql::Constraint::Builder::Trigger.validation_builders_factory.register_builders(
51
+ Mv::Postgresql::Validation::Exclusion => Mv::Postgresql::Validation::Builder::Trigger::Exclusion,
52
+ Mv::Postgresql::Validation::Inclusion => Mv::Postgresql::Validation::Builder::Trigger::Inclusion,
53
+ Mv::Postgresql::Validation::Length => Mv::Postgresql::Validation::Builder::Trigger::Length,
54
+ Mv::Postgresql::Validation::Format => Mv::Postgresql::Validation::Builder::Trigger::Format,
55
+ Mv::Postgresql::Validation::Presence => Mv::Postgresql::Validation::Builder::Trigger::Presence,
56
+ Mv::Postgresql::Validation::Absence => Mv::Postgresql::Validation::Builder::Trigger::Absence,
57
+ Mv::Core::Validation::Uniqueness => Mv::Postgresql::Validation::Builder::Trigger::Uniqueness
58
+ )
59
+
60
+ #validation builders in check
61
+ Mv::Postgresql::Constraint::Builder::Check.validation_builders_factory.register_builders(
62
+ Mv::Postgresql::Validation::Exclusion => Mv::Postgresql::Validation::Builder::Exclusion,
63
+ Mv::Postgresql::Validation::Inclusion => Mv::Postgresql::Validation::Builder::Inclusion,
64
+ Mv::Postgresql::Validation::Length => Mv::Core::Validation::Builder::Length,
65
+ Mv::Postgresql::Validation::Format => Mv::Postgresql::Validation::Builder::Format,
66
+ Mv::Postgresql::Validation::Presence => Mv::Core::Validation::Builder::Presence,
67
+ Mv::Postgresql::Validation::Absence => Mv::Core::Validation::Builder::Absence
68
+ )
69
+
70
+ end
4
71
 
@@ -0,0 +1,11 @@
1
+ module Mv
2
+ module Postgresql
3
+ module ActiveRecord
4
+ module ConnectionAdapters
5
+ module PostgresqlAdapterDecorator
6
+ include Mv::Core::ActiveRecord::ConnectionAdapters::AbstractAdapterDecorator
7
+ end
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,45 @@
1
+ module Mv
2
+ module Postgresql
3
+ module Constraint
4
+ module Builder
5
+ class Check < Mv::Core::Constraint::Builder::Base
6
+ def create
7
+ validation_builders.group_by(&:table_name).each do |table_name, validations|
8
+ db.execute(drop_check_statement(table_name))
9
+ db.execute(create_check_statement(table_name))
10
+ end
11
+ end
12
+
13
+ def update new_constraint_builder
14
+ delete
15
+ new_constraint_builder.create
16
+ end
17
+
18
+ def delete
19
+ validation_builders.group_by(&:table_name).each do |table_name, validations|
20
+ if db.table_exists?(table_name)
21
+ db.execute(drop_check_statement(table_name))
22
+ end
23
+ end
24
+ end
25
+
26
+ private
27
+
28
+ def check_body(table_name)
29
+ validation_builders.select{|b| b.table_name == table_name }.collect(&:conditions).flatten.collect do |condition|
30
+ "(#{condition[:statement]})"
31
+ end.join(" AND ")
32
+ end
33
+
34
+ def create_check_statement(table_name)
35
+ "ALTER TABLE #{table_name} ADD CONSTRAINT #{name} CHECK (#{check_body(table_name)});"
36
+ end
37
+
38
+ def drop_check_statement(table_name)
39
+ "ALTER TABLE #{table_name} DROP CONSTRAINT IF EXISTS #{name};"
40
+ end
41
+ end
42
+ end
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,69 @@
1
+ module Mv
2
+ module Postgresql
3
+ module Constraint
4
+ module Builder
5
+ class Trigger < Mv::Core::Constraint::Builder::Trigger
6
+ def create
7
+ validation_builders.group_by(&:table_name).each do |table_name, validations|
8
+ db.execute(drop_trigger_statement(table_name))
9
+ db.execute(drop_function_statement())
10
+ db.execute(create_function_statement(table_name))
11
+ db.execute(create_trigger_statement(table_name))
12
+ end
13
+ end
14
+
15
+ def delete
16
+ validation_builders.group_by(&:table_name).each do |table_name, validations|
17
+ if db.table_exists?(table_name)
18
+ db.execute(drop_trigger_statement(table_name))
19
+ db.execute(drop_function_statement())
20
+ end
21
+ end
22
+ end
23
+
24
+ def update new_constraint_builder
25
+ delete
26
+ new_constraint_builder.create
27
+ end
28
+
29
+ private
30
+
31
+ def func_name
32
+ "#{name}_func"
33
+ end
34
+
35
+ def drop_trigger_statement table_name
36
+ "DROP TRIGGER IF EXISTS #{name} ON #{table_name};"
37
+ end
38
+
39
+ def create_trigger_statement table_name
40
+ "CREATE TRIGGER #{name} BEFORE #{update? ? 'UPDATE' : 'INSERT'} ON #{table_name}
41
+ FOR EACH ROW EXECUTE PROCEDURE #{func_name}();".squish
42
+ end
43
+
44
+ def function_body(table_name)
45
+ validation_builders.select{|b| b.table_name == table_name }.collect(&:conditions).flatten.collect do |condition|
46
+ "IF NOT(#{condition[:statement]}) THEN
47
+ RAISE EXCEPTION '#{condition[:message]}';
48
+ END IF".squish
49
+ end.join("; \n")
50
+ end
51
+
52
+ def drop_function_statement
53
+ "DROP FUNCTION IF EXISTS #{func_name}();"
54
+ end
55
+
56
+ def create_function_statement table_name
57
+ "CREATE FUNCTION #{func_name}() RETURNS TRIGGER AS $#{func_name}$
58
+ BEGIN
59
+ #{function_body(table_name)};
60
+
61
+ RETURN NEW;
62
+ END;
63
+ $#{func_name}$ LANGUAGE plpgsql;"
64
+ end
65
+ end
66
+ end
67
+ end
68
+ end
69
+ end
@@ -0,0 +1,11 @@
1
+ module Mv
2
+ module Postgresql
3
+ module Constraint
4
+ class Check < Mv::Core::Constraint::Base
5
+ def initialize description
6
+ super
7
+ end
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,11 @@
1
+ require 'mv/postgresql/active_record/connection_adapters/postgresql_adapter_decorator'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ class Railtie < ::Rails::Railtie
6
+ initializer 'mv-postgresql.initialization', after: 'active_record.initialize_database' do
7
+ ::ActiveRecord::ConnectionAdapters::PostgreSQLAdapter.send(:prepend, Mv::Postgresql::ActiveRecord::ConnectionAdapters::PostgresqlAdapterDecorator)
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,17 @@
1
+ module Mv
2
+ module Postgresql
3
+ module Route
4
+ class Check
5
+ attr_reader :validation
6
+
7
+ def initialize(validation)
8
+ @validation = validation
9
+ end
10
+
11
+ def route
12
+ [Mv::Core::Constraint::Description.new(validation.check_name, :check)]
13
+ end
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,11 @@
1
+ require 'mv/postgresql/validation/check_support'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ module Validation
6
+ class Absence < Mv::Core::Validation::Absence
7
+ include CheckSupport
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,18 @@
1
+ module Mv
2
+ module Postgresql
3
+ module Validation
4
+ module Builder
5
+ class Exclusion < Mv::Core::Validation::Builder::Exclusion
6
+ protected
7
+
8
+ def db_value value
9
+ return "'#{value.strftime('%Y-%m-%d %H:%M:%S')}'" if value.is_a?(DateTime)
10
+ return "'#{value.strftime('%Y-%m-%d %H:%M:%S')}'" if value.is_a?(Time)
11
+ return "'#{value.strftime('%Y-%m-%d')}'" if value.is_a?(Date)
12
+ super
13
+ end
14
+ end
15
+ end
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,34 @@
1
+ module Mv
2
+ module Postgresql
3
+ module Validation
4
+ module Builder
5
+ class Format < Mv::Core::Validation::Builder::Base
6
+ delegate :with, to: :validation
7
+
8
+ def conditions
9
+ [{
10
+ statement: apply_allow_nil_and_blank(apply_with(column_reference)),
11
+ message: message
12
+ }]
13
+ end
14
+
15
+ protected
16
+
17
+ def db_value value
18
+ return "'#{value.source}'" if value.is_a?(Regexp)
19
+ return "'#{value.to_s}'" if value.is_a?(String)
20
+ raise Mv::Core::Error.new(table_name: table_name,
21
+ column_name: column_name,
22
+ validation_type: :inclusion,
23
+ options: { in: value },
24
+ error: "#{value.class} is not supported as :with value")
25
+ end
26
+
27
+ def apply_with stmt
28
+ "#{stmt} ~ #{db_value(with)}"
29
+ end
30
+ end
31
+ end
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,18 @@
1
+ module Mv
2
+ module Postgresql
3
+ module Validation
4
+ module Builder
5
+ class Inclusion < Mv::Core::Validation::Builder::Inclusion
6
+ protected
7
+
8
+ def db_value value
9
+ return "'#{value.strftime('%Y-%m-%d %H:%M:%S')}'" if value.is_a?(DateTime)
10
+ return "'#{value.strftime('%Y-%m-%d %H:%M:%S')}'" if value.is_a?(Time)
11
+ return "'#{value.strftime('%Y-%m-%d')}'" if value.is_a?(Date)
12
+ super
13
+ end
14
+ end
15
+ end
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,15 @@
1
+ require 'mv/postgresql/validation/builder/trigger/trigger_column'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ module Validation
6
+ module Builder
7
+ module Trigger
8
+ class Absence < Mv::Core::Validation::Builder::Absence
9
+ include TriggerColumn
10
+ end
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,16 @@
1
+ require 'mv/postgresql/validation/builder/exclusion'
2
+ require 'mv/postgresql/validation/builder/trigger/trigger_column'
3
+
4
+ module Mv
5
+ module Postgresql
6
+ module Validation
7
+ module Builder
8
+ module Trigger
9
+ class Exclusion < Mv::Postgresql::Validation::Builder::Exclusion
10
+ include TriggerColumn
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,16 @@
1
+ require 'mv/postgresql/validation/builder/format'
2
+ require 'mv/postgresql/validation/builder/trigger/trigger_column'
3
+
4
+ module Mv
5
+ module Postgresql
6
+ module Validation
7
+ module Builder
8
+ module Trigger
9
+ class Format < Mv::Postgresql::Validation::Builder::Format
10
+ include TriggerColumn
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,16 @@
1
+ require 'mv/postgresql/validation/builder/inclusion'
2
+ require 'mv/postgresql/validation/builder/trigger/trigger_column'
3
+
4
+ module Mv
5
+ module Postgresql
6
+ module Validation
7
+ module Builder
8
+ module Trigger
9
+ class Inclusion < Mv::Postgresql::Validation::Builder::Inclusion
10
+ include TriggerColumn
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,15 @@
1
+ require 'mv/postgresql/validation/builder/trigger/trigger_column'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ module Validation
6
+ module Builder
7
+ module Trigger
8
+ class Length < Mv::Core::Validation::Builder::Length
9
+ include TriggerColumn
10
+ end
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,15 @@
1
+ require 'mv/postgresql/validation/builder/trigger/trigger_column'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ module Validation
6
+ module Builder
7
+ module Trigger
8
+ class Presence < Mv::Core::Validation::Builder::Presence
9
+ include TriggerColumn
10
+ end
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,17 @@
1
+ module Mv
2
+ module Postgresql
3
+ module Validation
4
+ module Builder
5
+ module Trigger
6
+ module TriggerColumn
7
+ protected
8
+
9
+ def column_reference
10
+ "NEW.#{super}"
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,15 @@
1
+ require 'mv/postgresql/validation/builder/trigger/trigger_column'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ module Validation
6
+ module Builder
7
+ module Trigger
8
+ class Uniqueness < Mv::Core::Validation::Builder::Uniqueness
9
+ include TriggerColumn
10
+ end
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,44 @@
1
+ module Mv
2
+ module Postgresql
3
+ module Validation
4
+ module CheckSupport
5
+ attr_reader :check_name
6
+
7
+ def self.included mod
8
+ mod.validates :check_name, absence: { message: 'allowed when :as == :trigger' }, unless: :check?
9
+ end
10
+
11
+ def initialize(table_name, column_name, opts)
12
+ super
13
+
14
+ @check_name = opts.with_indifferent_access[:check_name] || default_check_name
15
+ end
16
+
17
+ def to_a
18
+ super + [check_name.to_s]
19
+ end
20
+
21
+ protected
22
+
23
+ def available_as
24
+ super + [:check]
25
+ end
26
+
27
+ def default_as
28
+ :check
29
+ end
30
+
31
+ def default_check_name
32
+ "chk_mv_#{table_name}_#{column_name}" if check?
33
+ end
34
+
35
+ private
36
+
37
+ def check?
38
+ as.try(:to_sym) == :check
39
+ end
40
+
41
+ end
42
+ end
43
+ end
44
+ end
@@ -0,0 +1,11 @@
1
+ require 'mv/postgresql/validation/check_support'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ module Validation
6
+ class Exclusion < Mv::Core::Validation::Exclusion
7
+ include CheckSupport
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,25 @@
1
+ require 'mv/postgresql/validation/check_support'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ module Validation
6
+ class Format < Mv::Core::Validation::Base
7
+ include CheckSupport
8
+
9
+ attr_reader :with
10
+
11
+ validates :with, presence: true
12
+
13
+ def initialize(table_name, column_name, opts)
14
+ super(table_name, column_name, opts)
15
+
16
+ @with = opts.with_indifferent_access[:with]
17
+ end
18
+
19
+ def to_a
20
+ super + [with.to_s]
21
+ end
22
+ end
23
+ end
24
+ end
25
+ end
@@ -0,0 +1,11 @@
1
+ require 'mv/postgresql/validation/check_support'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ module Validation
6
+ class Inclusion < Mv::Core::Validation::Inclusion
7
+ include CheckSupport
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,11 @@
1
+ require 'mv/postgresql/validation/check_support'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ module Validation
6
+ class Length < Mv::Core::Validation::Length
7
+ include CheckSupport
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,11 @@
1
+ require 'mv/postgresql/validation/check_support'
2
+
3
+ module Mv
4
+ module Postgresql
5
+ module Validation
6
+ class Presence < Mv::Core::Validation::Presence
7
+ include CheckSupport
8
+ end
9
+ end
10
+ end
11
+ end
metadata CHANGED
@@ -1,15 +1,29 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mv-postgresql
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.1
4
+ version: 2.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Valeriy Prokopchuk
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-11-07 00:00:00.000000000 Z
11
+ date: 2015-01-17 00:00:00.000000000 Z
12
12
  dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: railties
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ~>
18
+ - !ruby/object:Gem::Version
19
+ version: '4.1'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ~>
25
+ - !ruby/object:Gem::Version
26
+ version: '4.1'
13
27
  - !ruby/object:Gem::Dependency
14
28
  name: pg
15
29
  requirement: !ruby/object:Gem::Requirement
@@ -30,14 +44,14 @@ dependencies:
30
44
  requirements:
31
45
  - - ~>
32
46
  - !ruby/object:Gem::Version
33
- version: '1.0'
47
+ version: '2.0'
34
48
  type: :runtime
35
49
  prerelease: false
36
50
  version_requirements: !ruby/object:Gem::Requirement
37
51
  requirements:
38
52
  - - ~>
39
53
  - !ruby/object:Gem::Version
40
- version: '1.0'
54
+ version: '2.0'
41
55
  - !ruby/object:Gem::Dependency
42
56
  name: jeweler
43
57
  requirement: !ruby/object:Gem::Requirement
@@ -52,18 +66,97 @@ dependencies:
52
66
  - - ~>
53
67
  - !ruby/object:Gem::Version
54
68
  version: '2.0'
69
+ - !ruby/object:Gem::Dependency
70
+ name: rspec
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ~>
74
+ - !ruby/object:Gem::Version
75
+ version: '3.1'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - ~>
81
+ - !ruby/object:Gem::Version
82
+ version: '3.1'
83
+ - !ruby/object:Gem::Dependency
84
+ name: rspec-its
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ~>
88
+ - !ruby/object:Gem::Version
89
+ version: '1.1'
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ~>
95
+ - !ruby/object:Gem::Version
96
+ version: '1.1'
97
+ - !ruby/object:Gem::Dependency
98
+ name: guard-rspec
99
+ requirement: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - ~>
102
+ - !ruby/object:Gem::Version
103
+ version: '4.5'
104
+ type: :development
105
+ prerelease: false
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ requirements:
108
+ - - ~>
109
+ - !ruby/object:Gem::Version
110
+ version: '4.5'
111
+ - !ruby/object:Gem::Dependency
112
+ name: shoulda
113
+ requirement: !ruby/object:Gem::Requirement
114
+ requirements:
115
+ - - ~>
116
+ - !ruby/object:Gem::Version
117
+ version: '3.5'
118
+ type: :development
119
+ prerelease: false
120
+ version_requirements: !ruby/object:Gem::Requirement
121
+ requirements:
122
+ - - ~>
123
+ - !ruby/object:Gem::Version
124
+ version: '3.5'
55
125
  description: Migration Validators project postgresql driver
56
126
  email: vprokopchuk@gmail.com
57
127
  executables: []
58
128
  extensions: []
59
129
  extra_rdoc_files:
60
130
  - LICENSE.txt
61
- - README.rdoc
131
+ - README.md
62
132
  files:
63
133
  - LICENSE.txt
64
- - README.rdoc
65
- - lib/migration_validators/adapters/postgresql.rb
134
+ - README.md
66
135
  - lib/mv-postgresql.rb
136
+ - lib/mv/postgresql/active_record/connection_adapters/postgresql_adapter_decorator.rb
137
+ - lib/mv/postgresql/constraint/builder/check.rb
138
+ - lib/mv/postgresql/constraint/builder/trigger.rb
139
+ - lib/mv/postgresql/constraint/check.rb
140
+ - lib/mv/postgresql/railtie.rb
141
+ - lib/mv/postgresql/route/check.rb
142
+ - lib/mv/postgresql/validation/absence.rb
143
+ - lib/mv/postgresql/validation/builder/exclusion.rb
144
+ - lib/mv/postgresql/validation/builder/format.rb
145
+ - lib/mv/postgresql/validation/builder/inclusion.rb
146
+ - lib/mv/postgresql/validation/builder/trigger/absence.rb
147
+ - lib/mv/postgresql/validation/builder/trigger/exclusion.rb
148
+ - lib/mv/postgresql/validation/builder/trigger/format.rb
149
+ - lib/mv/postgresql/validation/builder/trigger/inclusion.rb
150
+ - lib/mv/postgresql/validation/builder/trigger/length.rb
151
+ - lib/mv/postgresql/validation/builder/trigger/presence.rb
152
+ - lib/mv/postgresql/validation/builder/trigger/trigger_column.rb
153
+ - lib/mv/postgresql/validation/builder/trigger/uniqueness.rb
154
+ - lib/mv/postgresql/validation/check_support.rb
155
+ - lib/mv/postgresql/validation/exclusion.rb
156
+ - lib/mv/postgresql/validation/format.rb
157
+ - lib/mv/postgresql/validation/inclusion.rb
158
+ - lib/mv/postgresql/validation/length.rb
159
+ - lib/mv/postgresql/validation/presence.rb
67
160
  homepage: http://github.com/vprokopchuk256/mv-postgresql
68
161
  licenses:
69
162
  - MIT
@@ -84,7 +177,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
84
177
  version: '0'
85
178
  requirements: []
86
179
  rubyforge_project:
87
- rubygems_version: 2.4.2
180
+ rubygems_version: 2.4.4
88
181
  signing_key:
89
182
  specification_version: 4
90
183
  summary: Migration Validators project postgresql driver
@@ -1,146 +0,0 @@
1
- module MigrationValidators
2
- module Adapters
3
- class Postgresql < MigrationValidators::Adapters::Base
4
- def name
5
- "PostgreSQL Migration Validators Adapter"
6
- end
7
-
8
- define_base_syntax
9
- syntax do
10
- operation(:regexp) {|stmt, value| "#{stmt} ~ #{value}"}
11
- operation :db_value do |value|
12
- case value.class.name
13
- when "String" then "'#{value}'"
14
- when "Date" then "'#{value.strftime('%Y-%m-%d')}' "
15
- when "DateTime" then "'#{value.strftime('%Y-%m-%d %H:%M:%S')}'"
16
- when "Time" then "'#{value.strftime('%Y-%m-%d %H:%M:%S')}' "
17
- when "Regexp" then "'#{value.source}'"
18
- else value.to_s
19
- end
20
- end
21
- end
22
-
23
- define_base_validators
24
-
25
- define_base_containers
26
- container :insert_trigger do
27
- operation :create do |stmt, trigger_name, group_name|
28
- func_name = "#{trigger_name}_func"
29
-
30
- "CREATE OR REPLACE FUNCTION #{func_name}() RETURNS TRIGGER AS $#{func_name}$
31
- BEGIN
32
- #{stmt};
33
-
34
- RETURN NEW;
35
- END;
36
- $#{func_name}$ LANGUAGE plpgsql;
37
-
38
- CREATE TRIGGER #{trigger_name} BEFORE INSERT ON #{group_name.first}
39
- FOR EACH ROW EXECUTE PROCEDURE #{func_name}();"
40
- end
41
-
42
- operation :drop do |stmt, trigger_name, group_name|
43
- "DROP TRIGGER IF EXISTS #{trigger_name} ON #{group_name.first};"
44
- end
45
-
46
-
47
- operation :bind_to_error do |stmt, error_message|
48
- "IF NOT(#{stmt}) THEN
49
- RAISE EXCEPTION '#{error_message}';
50
- END IF"
51
- end
52
- end
53
-
54
- container :update_trigger do
55
- operation :create do |stmt, trigger_name, group_name|
56
- func_name = "#{trigger_name}_func"
57
-
58
- "CREATE OR REPLACE FUNCTION #{func_name}() RETURNS TRIGGER AS $#{func_name}$
59
- BEGIN
60
- #{stmt};
61
-
62
- RETURN NEW;
63
- END;
64
- $#{func_name}$ LANGUAGE plpgsql;
65
-
66
- CREATE TRIGGER #{trigger_name} BEFORE UPDATE ON #{group_name.first}
67
- FOR EACH ROW EXECUTE PROCEDURE #{func_name}();"
68
- end
69
-
70
- operation :drop do |stmt, trigger_name, group_name|
71
- func_name = "#{trigger_name}_func"
72
-
73
- "DROP TRIGGER IF EXISTS #{trigger_name} ON #{group_name.first};
74
- DROP FUNCTION IF EXISTS #{func_name}();"
75
- end
76
-
77
- operation :bind_to_error do |stmt, error_message|
78
- "IF NOT(#{stmt}) THEN
79
- RAISE EXCEPTION '#{error_message}';
80
- END IF"
81
- end
82
- end
83
-
84
- container :check do
85
- operation :drop do |stmt, check_name, group_name|
86
- "CREATE OR REPLACE FUNCTION __temporary_constraint_drop_function__() RETURNS INTEGER AS $$
87
- DECLARE
88
- constraint_rec RECORD;
89
- BEGIN
90
- SELECT INTO constraint_rec * FROM pg_constraint WHERE conname='#{check_name}' AND contype='c';
91
-
92
- IF FOUND THEN
93
- ALTER TABLE #{group_name.first} DROP CONSTRAINT #{check_name};
94
- END IF;
95
-
96
- RETURN 1;
97
- END;
98
- $$ LANGUAGE plpgsql;
99
-
100
- SELECT __temporary_constraint_drop_function__();
101
-
102
- DROP FUNCTION __temporary_constraint_drop_function__();
103
- "
104
- end
105
- end
106
-
107
-
108
- route :presence, :trigger do
109
- to :insert_trigger, :if => {:on => [:save, :create, nil]}
110
- to :update_trigger, :if => {:on => [:save, :update, nil]}
111
- end
112
- route :presence, :check, :to => :check, :default => true
113
-
114
- route :inclusion, :trigger do
115
- to :insert_trigger, :if => {:on => [:save, :create, nil]}
116
- to :update_trigger, :if => {:on => [:save, :update, nil]}
117
- end
118
- route :inclusion, :check, :to => :check, :default => true
119
-
120
- route :exclusion, :trigger do
121
- to :insert_trigger, :if => {:on => [:save, :create, nil]}
122
- to :update_trigger, :if => {:on => [:save, :update, nil]}
123
- end
124
- route :exclusion, :check, :to => :check, :default => true
125
-
126
- route :length, :trigger do
127
- to :insert_trigger, :if => {:on => [:save, :create, nil]}
128
- to :update_trigger, :if => {:on => [:save, :update, nil]}
129
- end
130
- route :length, :check, :to => :check, :default => true
131
-
132
- route :format, :trigger do
133
- to :insert_trigger, :if => {:on => [:save, :create, nil]}
134
- to :update_trigger, :if => {:on => [:save, :update, nil]}
135
- end
136
- route :format, :check, :to => :check, :default => true
137
-
138
- route :uniqueness, :trigger do
139
- to :insert_trigger, :if => {:on => [:save, :create, nil]}
140
- to :update_trigger, :if => {:on => [:save, :update, nil]}
141
- end
142
- end
143
-
144
- MigrationValidators.register_adapter! "postgresql", Postgresql
145
- end
146
- end