aws-record-generator 1.0.0.pre.1

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.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 88db52d888ba8ab309db4f229686bc1cb036397d
4
+ data.tar.gz: 7ee3a11e989280135d8854d3eadf6acf04a7ac7d
5
+ SHA512:
6
+ metadata.gz: 47607097dc142faee512968f5845a2ef511c53fa11ece5f352804faac451f4895f2d1e54f168b0b538b5b1416cf9dbbd925f58d82563c308b98a56707e6580c7
7
+ data.tar.gz: cb09166ed00e62c040732380b38ffde75a37065cb8755c2589f473ec12092d6b38513612c67c16681f4d73dd31f60c0638fcf3bf0632326c267b3531865dd2ca
@@ -0,0 +1,28 @@
1
+ # Copyright 2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License"). You may not
4
+ # use this file except in compliance with the License. A copy of the License is
5
+ # located at
6
+ #
7
+ # http://aws.amazon.com/apache2.0/
8
+ #
9
+ # or in the "license" file accompanying this file. This file is distributed on
10
+ # an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
11
+ # or implied. See the License for the specific language governing permissions
12
+ # and limitations under the License.
13
+
14
+ require_relative 'generators/generated_attribute'
15
+ require_relative 'generators/secondary_index'
16
+ require_relative 'generators/test_helper'
17
+ require_relative 'generators/aws_record/model/model_generator'
18
+
19
+ require 'aws-record'
20
+ require 'rails/railtie'
21
+
22
+ module AwsRecord
23
+ class Railtie < Rails::Railtie
24
+ rake_tasks do
25
+ load 'tasks/table_config_migrate_task.rake'
26
+ end
27
+ end
28
+ end
@@ -0,0 +1,21 @@
1
+ Description:
2
+ rails generator for aws-record models
3
+
4
+ Pass the name of the model (preferably in singular form), and an optional list of attributes
5
+
6
+ Attributes are declarations of the fields that you wish to store within a model. You can pass
7
+ a type and list of options for each attribtue in the form: `name:type:options` if you do not provide
8
+ a type, it is assumed that the attribute is of type `string_attr`
9
+
10
+ Each model should have an hkey, if one is not present a `uuid:hkey` will be created for you.
11
+
12
+ Timestamps are not added by default but you can add them using the `--timestamps` flag
13
+ More information can be found at: https://github.com/awslabs/aws-record-generator/blob/master/README.md
14
+
15
+ Example:
16
+ rails generate aws_record:model Forum forum_uuid:hkey post_id:rkey post_title post_body tags:sset:default_value{Set.new} created_at:datetime:d_attr_name{PostCreatedAtTime} moderation:boolean:default_value{false}
17
+
18
+ This will create:
19
+ app/models/forum.rb
20
+ db/table_config/forum_config.rb
21
+ lib/tasks/table_config_migrate_task.rake # This is created once the first time the generator is run
@@ -0,0 +1,230 @@
1
+ # Copyright 2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License"). You may not
4
+ # use this file except in compliance with the License. A copy of the License is
5
+ # located at
6
+ #
7
+ # http://aws.amazon.com/apache2.0/
8
+ #
9
+ # or in the "license" file accompanying this file. This file is distributed on
10
+ # an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
11
+ # or implied. See the License for the specific language governing permissions
12
+ # and limitations under the License.
13
+
14
+ require 'rails/generators'
15
+ require 'aws-record-generator'
16
+
17
+ module AwsRecord
18
+ module Generators
19
+ class ModelGenerator < Rails::Generators::NamedBase
20
+
21
+ source_root File.expand_path('../templates', __FILE__)
22
+ argument :attributes, type: :array, default: [], banner: "field[:type][:opts]...", desc: "Describes the fields in the model"
23
+ check_class_collision
24
+
25
+ class_option :disable_mutation_tracking, type: :boolean, desc: "Disables dirty tracking"
26
+ class_option :timestamps, type: :boolean, desc: "Adds created, updated timestamps to the model"
27
+ class_option :table_config, type: :hash, default: {}, banner: "primary:R-W [SecondaryIndex1:R-W]...", desc: "Declares the r/w units for the model as well as any secondary indexes", :required => true
28
+ class_option :gsi, type: :array, default: [], banner: "name:hkey{field_name}[,rkey{field_name},proj_type{ALL|KEYS_ONLY|INCLUDE}]...", desc: "Allows for the declaration of secondary indexes"
29
+
30
+ class_option :required, type: :array, default: [], banner: "field1...", desc: "A list of attributes that are required for an instance of the model"
31
+ class_option :length_validations, type: :hash, default: {}, banner: "field1:MIN-MAX...", desc: "Validations on the length of attributes in a model"
32
+
33
+ attr_accessor :primary_read_units, :primary_write_units, :gsi_rw_units, :gsis, :required_attrs, :length_validations
34
+
35
+ def create_model
36
+ template "model.rb", File.join("app/models", class_path, "#{file_name}.rb")
37
+ end
38
+
39
+ def create_table_config
40
+ template "table_config.rb", File.join("db/table_config", class_path, "#{file_name}_config.rb")
41
+ end
42
+
43
+ private
44
+
45
+ def initialize(args, *options)
46
+ @parse_errors = []
47
+
48
+ super
49
+ ensure_unique_fields
50
+ ensure_hkey
51
+ parse_gsis!
52
+ parse_table_config!
53
+ parse_validations!
54
+
55
+ if !@parse_errors.empty?
56
+ STDERR.puts "The following errors were encountered while trying to parse the given attributes"
57
+ STDERR.puts
58
+ STDERR.puts @parse_errors
59
+ STDERR.puts
60
+
61
+ abort("Please fix the errors before proceeding.")
62
+ end
63
+ end
64
+
65
+ def parse_attributes!
66
+
67
+ self.attributes = (attributes || []).map do |attr|
68
+ begin
69
+ GeneratedAttribute.parse(attr)
70
+ rescue ArgumentError => e
71
+ @parse_errors << e
72
+ next
73
+ end
74
+ end
75
+ self.attributes = self.attributes.compact
76
+
77
+ if options['timestamps']
78
+ self.attributes << GeneratedAttribute.parse("created:datetime:default_value{Time.now}")
79
+ self.attributes << GeneratedAttribute.parse("updated:datetime:default_value{Time.now}")
80
+ end
81
+ end
82
+
83
+ def ensure_unique_fields
84
+ used_names = Set.new
85
+ duplicate_fields = []
86
+
87
+ self.attributes.each do |attr|
88
+
89
+ if used_names.include? attr.name
90
+ duplicate_fields << [:attribute, attr.name]
91
+ end
92
+ used_names.add attr.name
93
+
94
+ if attr.options.key? :database_attribute_name
95
+ raw_db_attr_name = attr.options[:database_attribute_name].delete('"') # db attribute names are wrapped with " to make template generation easier
96
+
97
+ if used_names.include? raw_db_attr_name
98
+ duplicate_fields << [:database_attribute_name, raw_db_attr_name]
99
+ end
100
+
101
+ used_names.add raw_db_attr_name
102
+ end
103
+ end
104
+
105
+ if !duplicate_fields.empty?
106
+ duplicate_fields.each do |invalid_attr|
107
+ @parse_errors << ArgumentError.new("Found duplicated field name: #{invalid_attr[1]}, in attribute#{invalid_attr[0]}")
108
+ end
109
+ end
110
+ end
111
+
112
+ def ensure_hkey
113
+ uuid_member = nil
114
+ hkey_member = nil
115
+ rkey_member = nil
116
+
117
+ self.attributes.each do |attr|
118
+ if attr.options.key? :hash_key
119
+ if hkey_member
120
+ @parse_errors << ArgumentError.new("Redefinition of hash_key attr: #{attr.name}, original declaration of hash_key on: #{hkey_member.name}")
121
+ next
122
+ end
123
+
124
+ hkey_member = attr
125
+ elsif attr.options.key? :range_key
126
+ if rkey_member
127
+ @parse_errors << ArgumentError.new("Redefinition of range_key attr: #{attr.name}, original declaration of range_key on: #{hkey_member.name}")
128
+ next
129
+ end
130
+
131
+ rkey_member = attr
132
+ end
133
+
134
+ if attr.name.include? "uuid"
135
+ uuid_member = attr
136
+ end
137
+ end
138
+
139
+ if !hkey_member
140
+ if uuid_member
141
+ uuid_member.options[:hash_key] = true
142
+ else
143
+ self.attributes.unshift GeneratedAttribute.parse("uuid:hkey")
144
+ end
145
+ end
146
+ end
147
+
148
+ def mutation_tracking_disabled?
149
+ options['disable_mutation_tracking']
150
+ end
151
+
152
+ def has_validations?
153
+ !@required_attrs.empty? || !@length_validations.empty?
154
+ end
155
+
156
+ def parse_table_config!
157
+ @primary_read_units, @primary_write_units = parse_rw_units("primary")
158
+
159
+ @gsi_rw_units = @gsis.map { |idx|
160
+ [idx.name, parse_rw_units(idx.name)]
161
+ }.to_h
162
+
163
+ options['table_config'].each do |config, rw_units|
164
+ if config == "primary"
165
+ next
166
+ else
167
+ gsi = @gsis.select { |idx| idx.name == config}
168
+
169
+ if gsi.empty?
170
+ @parse_errors << ArgumentError.new("Could not find a gsi declaration for #{config}")
171
+ end
172
+ end
173
+ end
174
+ end
175
+
176
+ def parse_rw_units(name)
177
+ if !options['table_config'].key? name
178
+ @parse_errors << ArgumentError.new("Please provide a table_config definition for #{name}")
179
+ else
180
+ rw_units = options['table_config'][name]
181
+ return rw_units.gsub(/[,.-]/, ':').split(':').reject { |s| s.empty? }
182
+ end
183
+ end
184
+
185
+ def parse_gsis!
186
+ @gsis = (options['gsi'] || []).map do |raw_idx|
187
+ begin
188
+ idx = SecondaryIndex.parse(raw_idx)
189
+
190
+ attributes = self.attributes.select { |attr| attr.name == idx.hash_key}
191
+ if attributes.empty?
192
+ @parse_errors << ArgumentError.new("Could not find attribute #{idx.hash_key} for gsi #{idx.name} hkey")
193
+ next
194
+ end
195
+
196
+ if idx.range_key
197
+ attributes = self.attributes.select { |attr| attr.name == idx.range_key}
198
+ if attributes.empty?
199
+ @parse_errors << ArgumentError.new("Could not find attribute #{idx.range_key} for gsi #{idx.name} rkey")
200
+ next
201
+ end
202
+ end
203
+
204
+ idx
205
+ rescue ArgumentError => e
206
+ @parse_errors << e
207
+ next
208
+ end
209
+ end
210
+
211
+ @gsis = @gsis.compact
212
+ end
213
+
214
+ def parse_validations!
215
+ @required_attrs = options['required']
216
+ @required_attrs.each do |val_attr|
217
+ @parse_errors << ArgumentError.new("No such field #{val_attr} in required validations") if !self.attributes.any? { |attr| attr.name == val_attr }
218
+ end
219
+
220
+ @length_validations = options['length_validations'].map do |val_attr, bounds|
221
+ @parse_errors << ArgumentError.new("No such field #{val_attr} in required validations") if !self.attributes.any? { |attr| attr.name == val_attr }
222
+
223
+ bounds = bounds.gsub(/[,.-]/, ':').split(':').reject { |s| s.empty? }
224
+ [val_attr, "#{bounds[0]}..#{bounds[1]}"]
225
+ end
226
+ @length_validations = @length_validations.to_h
227
+ end
228
+ end
229
+ end
230
+ end
@@ -0,0 +1,33 @@
1
+ require 'aws-record'
2
+ <%= "require 'active_model'
3
+ " if has_validations? -%>
4
+
5
+ <% module_namespacing do -%>
6
+ class <%= class_name %>
7
+ include Aws::Record
8
+ <%= ' include ActiveModel::Validations
9
+ ' if has_validations? -%>
10
+ <%= ' disable_mutation_tracking
11
+ ' if mutation_tracking_disabled? -%>
12
+
13
+ <% attributes.each do |attribute| -%>
14
+ <%= attribute.type %> :<%= attribute.name %><% *opts, last_opt = attribute.options.to_a %><%= ', ' if last_opt %><% opts.each do |opt| %><%= opt[0] %>: <%= opt[1] %>, <% end %><% if last_opt %><%= last_opt[0] %>: <%= last_opt[1] %><% end %>
15
+ <% end -%>
16
+ <% gsis.each do |index| %>
17
+ global_secondary_index(
18
+ :<%= index.name %>,
19
+ hash_key: :<%= index.hash_key -%>,<%- if index.range_key %>
20
+ range_key: :<%= index.range_key -%>,<%- end %>
21
+ projection: {
22
+ projection_type: <%= index.projection_type %>
23
+ }
24
+ )
25
+ <% end -%>
26
+ <% if !required_attrs.empty? -%>
27
+ validates_presence_of <% *req, last_req = required_attrs -%><% req.each do |required_validation|-%>:<%= required_validation %>, <% end -%>:<%= last_req %>
28
+ <% end -%>
29
+ <% length_validations.each do |attribute, validation| -%>
30
+ validates_length_of :<%= attribute %>, within: <%= validation %>
31
+ <% end -%>
32
+ end
33
+ <% end -%>
@@ -0,0 +1,18 @@
1
+ require 'aws-record'
2
+
3
+ module ModelTableConfig
4
+ def self.config
5
+ Aws::Record::TableConfig.define do |t|
6
+ t.model_class <%= class_name %>
7
+
8
+ t.read_capacity_units <%= primary_read_units %>
9
+ t.write_capacity_units <%= primary_write_units %>
10
+ <%- gsis.each do |index| %>
11
+ t.global_secondary_index(:<%= index.name %>) do |i|
12
+ i.read_capacity_units <%= gsi_rw_units[index.name][0] %>
13
+ i.write_capacity_units <%= gsi_rw_units[index.name][1] %>
14
+ end
15
+ <%- end -%>
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,110 @@
1
+ # Copyright 2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License"). You may not
4
+ # use this file except in compliance with the License. A copy of the License is
5
+ # located at
6
+ #
7
+ # http://aws.amazon.com/apache2.0/
8
+ #
9
+ # or in the "license" file accompanying this file. This file is distributed on
10
+ # an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
11
+ # or implied. See the License for the specific language governing permissions
12
+ # and limitations under the License.
13
+
14
+ module AwsRecord
15
+ module Generators
16
+ class GeneratedAttribute
17
+
18
+ OPTS = %w(hkey rkey persist_nil db_attr_name ddb_type default_value)
19
+ INVALID_HKEY_TYPES = %i(map_attr list_attr numeric_set_attr string_set_attr)
20
+ attr_reader :name, :type
21
+ attr_accessor :options
22
+
23
+ class << self
24
+
25
+ def parse(field_definition)
26
+ name, type, opts = field_definition.split(':')
27
+ type = "string" if not type
28
+ type, opts = "string", type if OPTS.any? { |opt| type.include? opt }
29
+
30
+ opts = opts.split(',') if opts
31
+ type, opts = parse_type_and_options(name, type, opts)
32
+ validate_opt_combs(name, type, opts)
33
+
34
+ new(name, type, opts)
35
+ end
36
+
37
+ private
38
+
39
+ def validate_opt_combs(name, type, opts)
40
+ if opts
41
+ is_hkey = opts.key?(:hash_key)
42
+ is_rkey = opts.key?(:range_key)
43
+
44
+ raise ArgumentError.new("Field #{name} cannot be a range key and hash key simultaneously") if is_hkey && is_rkey
45
+ raise ArgumentError.new("Field #{name} cannot be a hash key and be of type #{type}") if is_hkey and INVALID_HKEY_TYPES.include? type
46
+ end
47
+ end
48
+
49
+ def parse_type_and_options(name, type, opts)
50
+ opts = [] if not opts
51
+ return parse_type(name, type), opts.map { |opt| parse_option(name, opt) }.to_h
52
+ end
53
+
54
+ def parse_option(name, opt)
55
+ case opt
56
+
57
+ when "hkey"
58
+ return :hash_key, true
59
+ when "rkey"
60
+ return :range_key, true
61
+ when "persist_nil"
62
+ return :persist_nil, true
63
+ when /db_attr_name\{(\w+)\}/
64
+ return :database_attribute_name, '"' + $1 + '"'
65
+ when /ddb_type\{(S|N|B|BOOL|SS|NS|BS|M|L)\}/i
66
+ return :dynamodb_type, '"' + $1.upcase + '"'
67
+ when /default_value\{(.+)\}/
68
+ return :default_value, $1
69
+ else
70
+ raise ArgumentError.new("You provided an invalid option for #{name}: #{opt}")
71
+ end
72
+ end
73
+
74
+ def parse_type(name, type)
75
+ case type.downcase
76
+
77
+ when "bool", "boolean"
78
+ :boolean_attr
79
+ when "date"
80
+ :date_attr
81
+ when "datetime"
82
+ :datetime_attr
83
+ when "float"
84
+ :float_attr
85
+ when "int", "integer"
86
+ :integer_attr
87
+ when "list"
88
+ :list_attr
89
+ when "map"
90
+ :map_attr
91
+ when "num_set", "numeric_set", "nset"
92
+ :numeric_set_attr
93
+ when "string_set", "s_set", "sset"
94
+ :string_set_attr
95
+ when "string"
96
+ :string_attr
97
+ else
98
+ raise ArgumentError.new("Invalid type for #{name}: #{type}")
99
+ end
100
+ end
101
+ end
102
+
103
+ def initialize(name, type = :string_attr, options = {})
104
+ @name = name
105
+ @type = type
106
+ @options = options
107
+ end
108
+ end
109
+ end
110
+ end
@@ -0,0 +1,73 @@
1
+ # Copyright 2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License"). You may not
4
+ # use this file except in compliance with the License. A copy of the License is
5
+ # located at
6
+ #
7
+ # http://aws.amazon.com/apache2.0/
8
+ #
9
+ # or in the "license" file accompanying this file. This file is distributed on
10
+ # an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
11
+ # or implied. See the License for the specific language governing permissions
12
+ # and limitations under the License.
13
+
14
+ module AwsRecord
15
+ module Generators
16
+ class SecondaryIndex
17
+
18
+ PROJ_TYPES = %w(ALL KEYS_ONLY INCLUDE)
19
+ attr_reader :name, :hash_key, :range_key, :projection_type
20
+
21
+ class << self
22
+ def parse(key_definition)
23
+ name, index_options = key_definition.split(':')
24
+ index_options = index_options.split(',') if index_options
25
+ opts = parse_raw_options(index_options)
26
+
27
+ new(name, opts)
28
+ end
29
+
30
+ private
31
+ def parse_raw_options(raw_opts)
32
+ raw_opts = [] if not raw_opts
33
+ raw_opts.map { |opt| get_option_value(opt) }.to_h
34
+ end
35
+
36
+ def get_option_value(raw_option)
37
+ case raw_option
38
+
39
+ when /hkey\{(\w+)\}/
40
+ return :hash_key, $1
41
+ when /rkey\{(\w+)\}/
42
+ return :range_key, $1
43
+ when /proj_type\{(\w+)\}/
44
+ return :projection_type, $1
45
+ else
46
+ raise ArgumentError.new("Invalid option for secondary index #{raw_option}")
47
+ end
48
+ end
49
+ end
50
+
51
+ def initialize(name, opts)
52
+ raise ArgumentError.new("You must provide a name") if not name
53
+ raise ArgumentError.new("You must provide a hash key") if not opts[:hash_key]
54
+
55
+ if opts.key? :projection_type
56
+ raise ArgumentError.new("Invalid projection type #{opts[:projection_type]}") if not PROJ_TYPES.include? opts[:projection_type]
57
+ raise NotImplementedError.new("ALL is the only projection type currently supported") if opts[:projection_type] != "ALL"
58
+ else
59
+ opts[:projection_type] = "ALL"
60
+ end
61
+
62
+ if opts[:hash_key] == opts[:range_key]
63
+ raise ArgumentError.new("#{opts[:hash_key]} cannot be both the rkey and hkey for gsi #{name}")
64
+ end
65
+
66
+ @name = name
67
+ @hash_key = opts[:hash_key]
68
+ @range_key = opts[:range_key]
69
+ @projection_type = '"' + "#{opts[:projection_type]}" + '"'
70
+ end
71
+ end
72
+ end
73
+ end
@@ -0,0 +1,79 @@
1
+ # Copyright 2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License"). You may not
4
+ # use this file except in compliance with the License. A copy of the License is
5
+ # located at
6
+ #
7
+ # http://aws.amazon.com/apache2.0/
8
+ #
9
+ # or in the "license" file accompanying this file. This file is distributed on
10
+ # an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
11
+ # or implied. See the License for the specific language governing permissions
12
+ # and limitations under the License.
13
+
14
+ require 'rails/generators/rails/app/app_generator'
15
+ require "rails/generators/testing/behaviour"
16
+ require "fileutils"
17
+ require "minitest/spec"
18
+
19
+ module AwsRecord
20
+ module Generators
21
+ class GeneratorTestHelper
22
+ include Minitest::Assertions
23
+ attr_accessor :assertions
24
+
25
+ include Rails::Generators::Testing::Behaviour
26
+ include FileUtils
27
+
28
+ def initialize(klass, dest)
29
+ @temp_root = File.expand_path(dest)
30
+
31
+ GeneratorTestHelper.tests klass
32
+ temp_app_dest = File.join(File.expand_path(@temp_root, __dir__), "test_app")
33
+ GeneratorTestHelper.destination temp_app_dest
34
+
35
+ destination_root_is_set?
36
+ prepare_destination
37
+ setup_test_app
38
+ ensure_current_path
39
+
40
+ self.assertions = 0
41
+ end
42
+
43
+ def run_in_test_app(cmd)
44
+ cd destination_root
45
+ a = `rails #{cmd}`
46
+
47
+ ensure_current_path
48
+ end
49
+
50
+ def assert_file(generated_file, actual_file)
51
+ assert File.exist?(generated_file), "Expected file #{generated_file.inspect} to exist, but does not"
52
+ assert File.exist?(actual_file), "Expected file #{actual_file.inspect} to exist, but does not"
53
+ assert identical? generated_file, actual_file
54
+ end
55
+
56
+ def assert_not_file(file_path)
57
+ assert !File.exist?(file_path), "Expected file #{file_path.inspect} to not exist, but does"
58
+ end
59
+
60
+ def cleanup
61
+ rm_rf @temp_root
62
+ end
63
+
64
+ def run_generator(args = default_arguments, config = {})
65
+ capture(:stderr) do
66
+ super
67
+ end
68
+ end
69
+
70
+ private
71
+
72
+ def setup_test_app
73
+ Rails::Generators::AppGenerator.start [destination_root, '--skip-bundle', '--skip-git', '--skip-spring', '--skip-test', '-d' , '--skip-javascript', '--force', '--quiet']
74
+ `echo 'gem "aws-record-generator", :path => "../../"' >> "#{destination_root}/Gemfile"`
75
+ `bundle install --gemfile "#{destination_root}/Gemfile"`
76
+ end
77
+ end
78
+ end
79
+ end
@@ -0,0 +1,26 @@
1
+ # Copyright 2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License"). You may not
4
+ # use this file except in compliance with the License. A copy of the License is
5
+ # located at
6
+ #
7
+ # http://aws.amazon.com/apache2.0/
8
+ #
9
+ # or in the "license" file accompanying this file. This file is distributed on
10
+ # an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
11
+ # or implied. See the License for the specific language governing permissions
12
+ # and limitations under the License.
13
+
14
+ desc "Run all table configs in table_config folder"
15
+
16
+ namespace :aws_record do
17
+ task migrate: :environment do
18
+ Dir[File.join('db', 'table_config', '**/*.rb')].each do |filename|
19
+ puts "running #{filename}"
20
+ load(filename)
21
+
22
+ table_config = ModelTableConfig.config
23
+ table_config.migrate! unless table_config.compatible?
24
+ end
25
+ end
26
+ end
metadata ADDED
@@ -0,0 +1,81 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: aws-record-generator
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0.pre.1
5
+ platform: ruby
6
+ authors:
7
+ - Amazon Web Services
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2018-06-13 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: aws-record
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '2'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '2'
27
+ - !ruby/object:Gem::Dependency
28
+ name: rails
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '4.2'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '4.2'
41
+ description: Rails generators for aws-record models
42
+ email:
43
+ - yasharm@amazon.com
44
+ executables: []
45
+ extensions: []
46
+ extra_rdoc_files: []
47
+ files:
48
+ - lib/aws-record-generator.rb
49
+ - lib/generators/aws_record/model/USAGE
50
+ - lib/generators/aws_record/model/model_generator.rb
51
+ - lib/generators/aws_record/model/templates/model.rb.tt
52
+ - lib/generators/aws_record/model/templates/table_config.rb.tt
53
+ - lib/generators/generated_attribute.rb
54
+ - lib/generators/secondary_index.rb
55
+ - lib/generators/test_helper.rb
56
+ - lib/tasks/table_config_migrate_task.rake
57
+ homepage: https://github.com/awslabs/aws-record-generator
58
+ licenses:
59
+ - Apache 2.0
60
+ metadata: {}
61
+ post_install_message:
62
+ rdoc_options: []
63
+ require_paths:
64
+ - lib
65
+ required_ruby_version: !ruby/object:Gem::Requirement
66
+ requirements:
67
+ - - ">="
68
+ - !ruby/object:Gem::Version
69
+ version: '0'
70
+ required_rubygems_version: !ruby/object:Gem::Requirement
71
+ requirements:
72
+ - - ">"
73
+ - !ruby/object:Gem::Version
74
+ version: 1.3.1
75
+ requirements: []
76
+ rubyforge_project:
77
+ rubygems_version: 2.6.13
78
+ signing_key:
79
+ specification_version: 4
80
+ summary: Rails generators for aws-record
81
+ test_files: []