k_domain 0.0.2 → 0.0.5
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/.rubocop.yml +31 -1
- data/STORIES.md +6 -2
- data/k_domain.gemspec +2 -0
- data/lib/k_domain/domain_model/dtos/_.rb +88 -0
- data/lib/k_domain/domain_model/dtos/belongs_to.rb +25 -0
- data/lib/k_domain/domain_model/dtos/column_old.rb +225 -0
- data/lib/k_domain/domain_model/dtos/dictionary/dictionary.rb +17 -0
- data/lib/k_domain/domain_model/dtos/domain.rb +11 -0
- data/lib/k_domain/domain_model/dtos/domain_statistics.rb +29 -0
- data/lib/k_domain/domain_model/dtos/entity.rb +338 -0
- data/lib/k_domain/domain_model/dtos/entity_statistics.rb +22 -0
- data/lib/k_domain/domain_model/dtos/foreign_key.rb +17 -0
- data/lib/k_domain/domain_model/dtos/has_and_belongs_to_many.rb +20 -0
- data/lib/k_domain/domain_model/dtos/has_many.rb +27 -0
- data/lib/k_domain/domain_model/dtos/has_one.rb +41 -0
- data/lib/k_domain/domain_model/dtos/investigate/investigate.rb +10 -0
- data/lib/k_domain/domain_model/dtos/investigate/issue.rb +13 -0
- data/lib/k_domain/domain_model/dtos/models/column.rb +49 -0
- data/lib/k_domain/domain_model/dtos/models/model.rb +111 -0
- data/lib/k_domain/domain_model/dtos/name_options.rb +10 -0
- data/lib/k_domain/domain_model/dtos/rails_controller.rb +10 -0
- data/lib/k_domain/domain_model/dtos/rails_model.rb +92 -0
- data/lib/k_domain/domain_model/dtos/related_entity.rb +36 -0
- data/lib/k_domain/domain_model/dtos/schema.rb +12 -0
- data/lib/k_domain/domain_model/dtos/statistics.rb +21 -0
- data/lib/k_domain/domain_model/dtos/validate.rb +25 -0
- data/lib/k_domain/domain_model/dtos/validates.rb +50 -0
- data/lib/k_domain/domain_model/load.rb +29 -0
- data/lib/k_domain/domain_model/transform.rb +94 -0
- data/lib/k_domain/domain_model/transform_steps/_.rb +9 -0
- data/lib/k_domain/domain_model/transform_steps/step.rb +123 -0
- data/lib/k_domain/domain_model/transform_steps/step1_attach_db_schema.rb +21 -0
- data/lib/k_domain/domain_model/transform_steps/step2_attach_models.rb +62 -0
- data/lib/k_domain/domain_model/transform_steps/step3_attach_columns.rb +137 -0
- data/lib/k_domain/domain_model/transform_steps/step4_attach_erd_files.rb +454 -0
- data/lib/k_domain/domain_model/transform_steps/step5_attach_dictionary.rb +56 -0
- data/lib/k_domain/raw_db_schema/dtos/_.rb +14 -0
- data/lib/k_domain/raw_db_schema/dtos/column.rb +16 -0
- data/lib/k_domain/raw_db_schema/dtos/database.rb +11 -0
- data/lib/k_domain/raw_db_schema/dtos/foreign_key.rb +14 -0
- data/lib/k_domain/raw_db_schema/dtos/index.rb +14 -0
- data/lib/k_domain/raw_db_schema/dtos/schema.rb +18 -0
- data/lib/k_domain/raw_db_schema/dtos/table.rb +21 -0
- data/lib/k_domain/raw_db_schema/dtos/unique_key.rb +14 -0
- data/lib/k_domain/raw_db_schema/load.rb +29 -0
- data/lib/k_domain/{raw_schema → raw_db_schema}/template.rb +0 -0
- data/lib/k_domain/{raw_schema → raw_db_schema}/transform.rb +37 -21
- data/lib/k_domain/version.rb +1 -1
- data/lib/k_domain.rb +14 -1
- metadata +74 -4
@@ -0,0 +1,92 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module KDomain
|
4
|
+
module DomainModel
|
5
|
+
# Rails model represents information that is found the model.rb class in the rails project
|
6
|
+
class RailsModel
|
7
|
+
attr_accessor :name
|
8
|
+
attr_accessor :name_plural
|
9
|
+
attr_accessor :name_original
|
10
|
+
attr_accessor :documentation_rel_path
|
11
|
+
attr_accessor :model_path
|
12
|
+
|
13
|
+
# @param [Symbol] value The value of ID has different meanings
|
14
|
+
# @option value :true Id column exists and it uses an Integer type
|
15
|
+
# @option value :false Id column does not exist
|
16
|
+
# @option value :bigserial Id column exists and it uses a BigSerial type
|
17
|
+
attr_accessor :id
|
18
|
+
|
19
|
+
attr_accessor :force
|
20
|
+
attr_accessor :primary_key
|
21
|
+
attr_accessor :quirks
|
22
|
+
|
23
|
+
attr_accessor :ruby_raw
|
24
|
+
attr_accessor :ruby_code
|
25
|
+
attr_accessor :ruby_frozen
|
26
|
+
attr_accessor :ruby_header
|
27
|
+
attr_accessor :ruby_code_public
|
28
|
+
attr_accessor :ruby_code_private
|
29
|
+
|
30
|
+
attr_accessor :default_scope
|
31
|
+
attr_accessor :scopes
|
32
|
+
attr_accessor :public_class_methods
|
33
|
+
attr_accessor :public_instance_methods
|
34
|
+
attr_accessor :private_instance_methods
|
35
|
+
|
36
|
+
# stats
|
37
|
+
attr_accessor :time_stamp1
|
38
|
+
attr_accessor :time_stamp2
|
39
|
+
attr_accessor :time_stamp3
|
40
|
+
|
41
|
+
def code_length
|
42
|
+
ruby_raw&.length
|
43
|
+
end
|
44
|
+
|
45
|
+
def display_quirks
|
46
|
+
quirks.join(' ')
|
47
|
+
end
|
48
|
+
|
49
|
+
def exists?
|
50
|
+
File.exist?(model_path)
|
51
|
+
end
|
52
|
+
|
53
|
+
def initialize
|
54
|
+
@quirks = []
|
55
|
+
end
|
56
|
+
|
57
|
+
def add_quirk(quirk)
|
58
|
+
@quirks << quirk
|
59
|
+
end
|
60
|
+
|
61
|
+
def to_h
|
62
|
+
{
|
63
|
+
name: name,
|
64
|
+
name_plural: name_plural,
|
65
|
+
name_original: name_original,
|
66
|
+
documentation_rel_path: documentation_rel_path,
|
67
|
+
model_path: model_path,
|
68
|
+
id: id,
|
69
|
+
force: force,
|
70
|
+
primary_key: primary_key,
|
71
|
+
quirks: quirks,
|
72
|
+
ruby_raw: ruby_raw,
|
73
|
+
ruby_code: ruby_code,
|
74
|
+
ruby_frozen: ruby_frozen,
|
75
|
+
ruby_header: ruby_header,
|
76
|
+
ruby_code_public: ruby_code_public,
|
77
|
+
ruby_code_private: ruby_code_private,
|
78
|
+
default_scope: default_scope,
|
79
|
+
scopes: scopes,
|
80
|
+
public_class_methods: public_class_methods,
|
81
|
+
public_instance_methods: public_instance_methods,
|
82
|
+
private_instance_methods: private_instance_methods,
|
83
|
+
time_stamp1: time_stamp1,
|
84
|
+
time_stamp2: time_stamp2,
|
85
|
+
time_stamp3: time_stamp3,
|
86
|
+
code_length: code_length,
|
87
|
+
exists: exists?
|
88
|
+
}
|
89
|
+
end
|
90
|
+
end
|
91
|
+
end
|
92
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module KDomain
|
4
|
+
module DomainModel
|
5
|
+
class RelatedEntity
|
6
|
+
# Name of the entity model
|
7
|
+
attr_accessor :name
|
8
|
+
attr_accessor :name_plural
|
9
|
+
attr_accessor :main_key
|
10
|
+
|
11
|
+
attr_accessor :trait1
|
12
|
+
attr_accessor :trait2
|
13
|
+
attr_accessor :trait3
|
14
|
+
|
15
|
+
def initialize(entity)
|
16
|
+
@name = entity.name
|
17
|
+
@name_plural = entity.name_plural
|
18
|
+
@main_key = entity.main_key
|
19
|
+
@trait1 = entity.trait1
|
20
|
+
@trait2 = entity.trait2
|
21
|
+
@trait3 = entity.trait3
|
22
|
+
end
|
23
|
+
|
24
|
+
def to_h
|
25
|
+
{
|
26
|
+
name: name,
|
27
|
+
name_plural: name_plural,
|
28
|
+
main_key: main_key,
|
29
|
+
trait1: trait1,
|
30
|
+
trait2: trait2,
|
31
|
+
trait3: trait3
|
32
|
+
}
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# DomainModel holds the entire domain model including database and ancillary information
|
4
|
+
module KDomain
|
5
|
+
module DomainModel
|
6
|
+
class Schema < Dry::Struct
|
7
|
+
attribute :domain , KDomain::DomainModel::Domain
|
8
|
+
attribute :database , KDomain::RawDbSchema::Schema
|
9
|
+
attribute :investigate , KDomain::DomainModel::Investigate
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
# module KDomain
|
3
|
+
# module DomainModel
|
4
|
+
# # Rails model represents information that is found the model.rb class in the rails project
|
5
|
+
# class Statistics
|
6
|
+
# attr_accessor :column_counts
|
7
|
+
# attr_accessor :code_counts
|
8
|
+
# attr_accessor :code_dsl_counts
|
9
|
+
# attr_accessor :data_counts
|
10
|
+
# attr_accessor :issues
|
11
|
+
|
12
|
+
# def initialize(meta)
|
13
|
+
# @column_counts = OpenStruct.new(meta[:column_counts])
|
14
|
+
# @code_counts = OpenStruct.new(meta[:code_counts])
|
15
|
+
# @code_dsl_counts = OpenStruct.new(meta[:code_dsl_counts])
|
16
|
+
# @data_counts = OpenStruct.new(meta[:data_counts])
|
17
|
+
# @issues = meta[:issues]
|
18
|
+
# end
|
19
|
+
# end
|
20
|
+
# end
|
21
|
+
# end
|
@@ -0,0 +1,25 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module KDomain
|
4
|
+
module DomainModel
|
5
|
+
class Validate
|
6
|
+
KEYS = [:on].freeze
|
7
|
+
|
8
|
+
attr_accessor :methods
|
9
|
+
|
10
|
+
attr_accessor :on
|
11
|
+
|
12
|
+
def format_on
|
13
|
+
for_template(on)
|
14
|
+
end
|
15
|
+
|
16
|
+
def for_template(value)
|
17
|
+
return nil if value.nil?
|
18
|
+
return value.to_s if value.is_a?(Hash)
|
19
|
+
return ":#{value}" if value.is_a?(Symbol)
|
20
|
+
|
21
|
+
value
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module KDomain
|
4
|
+
module DomainModel
|
5
|
+
class Validates
|
6
|
+
KEYS = %i[length unless format presence].freeze
|
7
|
+
|
8
|
+
attr_accessor :name
|
9
|
+
|
10
|
+
attr_accessor :length
|
11
|
+
attr_accessor :unless
|
12
|
+
attr_accessor :format
|
13
|
+
attr_accessor :presence
|
14
|
+
|
15
|
+
def format_length
|
16
|
+
for_template(length)
|
17
|
+
end
|
18
|
+
|
19
|
+
def format_unless
|
20
|
+
for_template(self.unless)
|
21
|
+
end
|
22
|
+
|
23
|
+
def format_format
|
24
|
+
for_template(self.format)
|
25
|
+
end
|
26
|
+
|
27
|
+
def format_presence
|
28
|
+
for_template(presence)
|
29
|
+
end
|
30
|
+
|
31
|
+
def for_template(value)
|
32
|
+
return nil if value.nil?
|
33
|
+
return value.to_s if value.is_a?(Hash)
|
34
|
+
return ":#{value}" if value.is_a?(Symbol)
|
35
|
+
|
36
|
+
value
|
37
|
+
end
|
38
|
+
|
39
|
+
def to_h
|
40
|
+
{
|
41
|
+
name: name,
|
42
|
+
length: length,
|
43
|
+
unless: self.unless,
|
44
|
+
format: self.format,
|
45
|
+
presence: presence
|
46
|
+
}
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# Annotates the original schema with methods that implement existing method calls
|
4
|
+
# that are already in the schema so that we can build a hash.
|
5
|
+
#
|
6
|
+
# Writes a new annotated schema.rb file with a public method called load that
|
7
|
+
# builds the hash
|
8
|
+
|
9
|
+
module KDomain
|
10
|
+
module DomainModel
|
11
|
+
class Load
|
12
|
+
include KLog::Logging
|
13
|
+
|
14
|
+
attr_reader :source_file
|
15
|
+
attr_reader :data
|
16
|
+
|
17
|
+
def initialize(source_file)
|
18
|
+
@source_file = source_file
|
19
|
+
end
|
20
|
+
|
21
|
+
def call
|
22
|
+
json = File.read(source_file)
|
23
|
+
data = KUtil.data.json_parse(json, as: :hash_symbolized)
|
24
|
+
|
25
|
+
@data = KDomain::DomainModel::Schema.new(data)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
@@ -0,0 +1,94 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# Loads the db schema object and works through a series of enrichment steps to
|
4
|
+
# that builds the domain modal
|
5
|
+
|
6
|
+
module KDomain
|
7
|
+
module DomainModel
|
8
|
+
class Transform
|
9
|
+
include KLog::Logging
|
10
|
+
|
11
|
+
attr_reader :db_schema
|
12
|
+
attr_reader :target_step_file
|
13
|
+
attr_reader :target_file
|
14
|
+
attr_reader :erd_path
|
15
|
+
|
16
|
+
def initialize(db_schema, target_file, target_step_file, erd_path)
|
17
|
+
@db_schema = db_schema
|
18
|
+
@target_step_file = target_step_file
|
19
|
+
@target_file = target_file
|
20
|
+
@erd_path = erd_path
|
21
|
+
end
|
22
|
+
|
23
|
+
def call
|
24
|
+
valid = true
|
25
|
+
valid &&= step1
|
26
|
+
valid &&= step2
|
27
|
+
valid &&= step3
|
28
|
+
valid &&= step4
|
29
|
+
valid &&= step5
|
30
|
+
|
31
|
+
raise 'DomainModal transform failed' unless valid
|
32
|
+
|
33
|
+
write
|
34
|
+
|
35
|
+
nil
|
36
|
+
end
|
37
|
+
|
38
|
+
def step1
|
39
|
+
Step1AttachDbSchema.run(domain_data, db_schema: db_schema)
|
40
|
+
write(step: '1-attach-db-schema')
|
41
|
+
end
|
42
|
+
|
43
|
+
def step2
|
44
|
+
Step2AttachModels.run(domain_data, erd_path: erd_path)
|
45
|
+
write(step: '2-attach-model')
|
46
|
+
end
|
47
|
+
|
48
|
+
def step3
|
49
|
+
Step3AttachColumns.run(domain_data)
|
50
|
+
write(step: '3-attach-columns')
|
51
|
+
end
|
52
|
+
|
53
|
+
def step4
|
54
|
+
Step4AttachErdFiles.run(domain_data, erd_path: erd_path)
|
55
|
+
write(step: '4-attach-erd-files')
|
56
|
+
end
|
57
|
+
|
58
|
+
def step5
|
59
|
+
Step5AttachDictionary.run(domain_data, erd_path: erd_path)
|
60
|
+
write(step: '5-attach-dictionary')
|
61
|
+
end
|
62
|
+
|
63
|
+
def write(step: nil)
|
64
|
+
file = if step.nil?
|
65
|
+
target_file
|
66
|
+
else
|
67
|
+
format(target_step_file, step: step)
|
68
|
+
end
|
69
|
+
FileUtils.mkdir_p(File.dirname(file))
|
70
|
+
File.write(file, JSON.pretty_generate(domain_data))
|
71
|
+
end
|
72
|
+
|
73
|
+
def domain_data
|
74
|
+
# The initial domain model structure is created here, but populated during the workflows.
|
75
|
+
@domain_data ||= {
|
76
|
+
domain: {
|
77
|
+
models: [],
|
78
|
+
erd_files: [],
|
79
|
+
dictionary: []
|
80
|
+
},
|
81
|
+
database: {
|
82
|
+
tables: [],
|
83
|
+
indexes: [],
|
84
|
+
foreign_keys: [],
|
85
|
+
meta: {}
|
86
|
+
},
|
87
|
+
investigate: {
|
88
|
+
issues: []
|
89
|
+
}
|
90
|
+
}
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
@@ -0,0 +1,9 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# The require order is important due to dependencies
|
4
|
+
require_relative './step'
|
5
|
+
require_relative './step1_attach_db_schema'
|
6
|
+
require_relative './step2_attach_models'
|
7
|
+
require_relative './step3_attach_columns'
|
8
|
+
require_relative './step4_attach_erd_files'
|
9
|
+
require_relative './step5_attach_dictionary'
|
@@ -0,0 +1,123 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module KDomain
|
4
|
+
module DomainModel
|
5
|
+
class Step
|
6
|
+
include KLog::Logging
|
7
|
+
|
8
|
+
attr_reader :domain_data
|
9
|
+
attr_reader :opts
|
10
|
+
attr_reader :valid
|
11
|
+
alias valid? valid
|
12
|
+
|
13
|
+
def initialize(domain_data, **opts)
|
14
|
+
# Useful for debugging
|
15
|
+
# log.info "Initialize #{self.class.name}"
|
16
|
+
|
17
|
+
@domain_data = domain_data
|
18
|
+
@opts = opts
|
19
|
+
@valid = true
|
20
|
+
end
|
21
|
+
|
22
|
+
def call; end
|
23
|
+
|
24
|
+
def self.run(domain_data, **opts)
|
25
|
+
step = new(domain_data, **opts)
|
26
|
+
step.call
|
27
|
+
step
|
28
|
+
end
|
29
|
+
|
30
|
+
def guard(message)
|
31
|
+
log.error message
|
32
|
+
@valid = false
|
33
|
+
end
|
34
|
+
|
35
|
+
# Domain Model Accessor/Helpers
|
36
|
+
def domain
|
37
|
+
guard('domain is missing') if domain_data[:domain].nil?
|
38
|
+
|
39
|
+
domain_data[:domain]
|
40
|
+
end
|
41
|
+
|
42
|
+
def domain_models
|
43
|
+
domain[:models]
|
44
|
+
end
|
45
|
+
|
46
|
+
# Database Accessor/Helpers
|
47
|
+
def database=(value)
|
48
|
+
domain_data[:database] = value
|
49
|
+
end
|
50
|
+
|
51
|
+
def database
|
52
|
+
guard('database is missing') if domain_data[:database].nil?
|
53
|
+
|
54
|
+
domain_data[:database]
|
55
|
+
end
|
56
|
+
|
57
|
+
def database_tables
|
58
|
+
guard('database_tables is missing') if database[:tables].nil?
|
59
|
+
|
60
|
+
database[:tables]
|
61
|
+
end
|
62
|
+
|
63
|
+
def database_foreign_keys
|
64
|
+
guard('database_foreign_keys is missing') if database[:foreign_keys].nil?
|
65
|
+
|
66
|
+
database[:foreign_keys]
|
67
|
+
end
|
68
|
+
|
69
|
+
def find_table_for_model(model)
|
70
|
+
database_tables.find { |table| table[:name] == model[:table_name] }
|
71
|
+
end
|
72
|
+
|
73
|
+
def table_name_exist?(table_name)
|
74
|
+
if table_name.nil?
|
75
|
+
guard('table_name_exist? was provided with a table_name: nil')
|
76
|
+
return false
|
77
|
+
end
|
78
|
+
database_table_name_hash.key?(table_name)
|
79
|
+
end
|
80
|
+
|
81
|
+
def find_foreign_table(lhs_table_name, column_name)
|
82
|
+
fk = database_foreign_keys.find { |foreign_key| foreign_key[:left] == lhs_table_name && foreign_key[:column] == column_name }
|
83
|
+
return fk[:right] if fk
|
84
|
+
|
85
|
+
nil
|
86
|
+
end
|
87
|
+
|
88
|
+
def investigate(step:, location:, key:, message:)
|
89
|
+
unique_key = build_key(step, location, key)
|
90
|
+
|
91
|
+
return if issue_hash.key?(unique_key)
|
92
|
+
|
93
|
+
value = { step: step, location: location, key: key, message: message }
|
94
|
+
|
95
|
+
issues << value # list
|
96
|
+
issue_hash[unique_key] = value # lookup
|
97
|
+
end
|
98
|
+
|
99
|
+
def issues
|
100
|
+
domain_data[:investigate][:issues]
|
101
|
+
end
|
102
|
+
|
103
|
+
private
|
104
|
+
|
105
|
+
def database_table_name_hash
|
106
|
+
@database_table_name_hash ||= database_tables.to_h { |table| [table[:name], table[:name]] }
|
107
|
+
end
|
108
|
+
|
109
|
+
def build_key(*values)
|
110
|
+
values.join('-')
|
111
|
+
end
|
112
|
+
|
113
|
+
def issue_hash
|
114
|
+
return @issue_hash if defined? @issue_hash
|
115
|
+
|
116
|
+
@issue_hash = issues.to_h do |issue|
|
117
|
+
unique_key = build_key(issue[:step], issue[:location], issue[:key])
|
118
|
+
[unique_key, issue]
|
119
|
+
end
|
120
|
+
end
|
121
|
+
end
|
122
|
+
end
|
123
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module KDomain
|
4
|
+
module DomainModel
|
5
|
+
class Step1AttachDbSchema < KDomain::DomainModel::Step
|
6
|
+
# Map database schema to domain model
|
7
|
+
def call
|
8
|
+
raise 'Schema not supplied' if opts[:db_schema].nil?
|
9
|
+
|
10
|
+
self.database = opts[:db_schema].clone
|
11
|
+
|
12
|
+
guard('tables are missing') if database[:tables].nil?
|
13
|
+
guard('indexes are missing') if database[:indexes].nil?
|
14
|
+
guard('foreign keys are missing') if database[:foreign_keys].nil?
|
15
|
+
guard('rails version is missing') if database[:meta][:rails].nil?
|
16
|
+
guard('postgres extensions are missing') if database[:meta][:database][:extensions].nil?
|
17
|
+
guard('unique keys are missing') if database[:meta][:unique_keys].nil?
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,62 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# Loop through the db_schema tables and build up a
|
4
|
+
# basic model for each table
|
5
|
+
class Step2AttachModels < KDomain::DomainModel::Step
|
6
|
+
# Map database schema to domain model
|
7
|
+
def call
|
8
|
+
raise 'ERD path not supplied' if opts[:erd_path].nil?
|
9
|
+
|
10
|
+
# Schema is re-shaped into a format designed for domain modeling
|
11
|
+
domain[:models] = database_tables.map { |table| model(table) }
|
12
|
+
end
|
13
|
+
|
14
|
+
def model(table)
|
15
|
+
table_name = table[:name].to_s
|
16
|
+
model_name = table_name.singularize
|
17
|
+
|
18
|
+
{
|
19
|
+
name: model_name,
|
20
|
+
name_plural: table_name, # need to check if this is correct as I know it is wrong for account_history_datum
|
21
|
+
table_name: table_name,
|
22
|
+
pk: primary_key(table),
|
23
|
+
erd_location: location(table_name, model_name),
|
24
|
+
statistics: {}, # Load in future step
|
25
|
+
columns: [] # Load in future step
|
26
|
+
}
|
27
|
+
end
|
28
|
+
|
29
|
+
def primary_key(table)
|
30
|
+
{
|
31
|
+
name: table[:primary_key],
|
32
|
+
type: table[:primary_key_type],
|
33
|
+
exist: !table[:primary_key].nil?
|
34
|
+
}
|
35
|
+
end
|
36
|
+
|
37
|
+
# Location of source code
|
38
|
+
def location(table_name, model_name)
|
39
|
+
file_normal = File.join(opts[:erd_path], "#{model_name}.rb")
|
40
|
+
file_custom = File.join(opts[:erd_path], "#{table_name}.rb")
|
41
|
+
file_exist = true
|
42
|
+
state = []
|
43
|
+
|
44
|
+
if File.exist?(file_normal)
|
45
|
+
file = file_normal
|
46
|
+
state.push(:has_ruby_model)
|
47
|
+
elsif File.exist?(file_custom)
|
48
|
+
file = file_custom
|
49
|
+
state.push(:has_ruby_model)
|
50
|
+
state.push(:nonconventional_name)
|
51
|
+
else
|
52
|
+
file = ''
|
53
|
+
file_exist = false
|
54
|
+
end
|
55
|
+
|
56
|
+
{
|
57
|
+
file: file,
|
58
|
+
exist: file_exist,
|
59
|
+
state: state # display_state: state.join(' ')
|
60
|
+
}
|
61
|
+
end
|
62
|
+
end
|