rails-erd 2.0.1 → 2.0.2
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/README.md +27 -0
- data/lib/rails_erd/cli.rb +5 -0
- data/lib/rails_erd/config.rb +5 -0
- data/lib/rails_erd/diagram.rb +68 -0
- data/lib/rails_erd/domain.rb +6 -4
- data/lib/rails_erd/version.rb +1 -1
- data/lib/rails_erd.rb +1 -0
- data/test/unit/config_test.rb +11 -0
- data/test/unit/diagram_test.rb +30 -0
- data/test/unit/domain_test.rb +13 -0
- metadata +2 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 4d47dd705b783be29e06d39d8bea92d6c5ac8019fba658e0279287b2197938d3
|
|
4
|
+
data.tar.gz: 1417646a7d2731ad2964e9cbac400cb3b2325f765ba1db610b44f28ffe03f699
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: cde6a9b96a0d3e5c03ccbed1c3e04e37d27efb3a37d2a09e1a5ff298cbb4e9ec3148065c551efe8da349315d7601420b3b98bccf049f4c83b782863a6a13f495
|
|
7
|
+
data.tar.gz: 5d53400f939b341b02becb90a5b4b413d4556a0fc36ef856d4c831d13ccc343ab0fd48772c8245ebedcdcdfee028068d51b1a09027ae809614c568bf19506505
|
data/README.md
CHANGED
|
@@ -70,6 +70,7 @@ sort: true
|
|
|
70
70
|
warn: true
|
|
71
71
|
title: true
|
|
72
72
|
exclude: null
|
|
73
|
+
exclude_attributes: null
|
|
73
74
|
only: null
|
|
74
75
|
only_recursion_depth: null
|
|
75
76
|
prepend_primary: false
|
|
@@ -77,6 +78,32 @@ cluster: false
|
|
|
77
78
|
splines: spline
|
|
78
79
|
```
|
|
79
80
|
|
|
81
|
+
### Hiding attributes for specific models
|
|
82
|
+
|
|
83
|
+
While `attributes: false` hides attributes for *every* model, `exclude_attributes`
|
|
84
|
+
lets you hide attributes for individual models without affecting the others. Map a
|
|
85
|
+
model name to `true` to hide all of its attributes, or to a list of attribute names
|
|
86
|
+
to hide only those:
|
|
87
|
+
|
|
88
|
+
```yaml
|
|
89
|
+
exclude_attributes:
|
|
90
|
+
BigTable: true # hide all attributes for BigTable
|
|
91
|
+
User: # hide only these attributes for User
|
|
92
|
+
- password_digest
|
|
93
|
+
- remember_token
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
From the command line, pass a comma separated list where each entry is either
|
|
97
|
+
`Model` (hide all of its attributes) or `Model.attribute` (hide a single one):
|
|
98
|
+
|
|
99
|
+
```bash
|
|
100
|
+
# rake task (bare key=value)
|
|
101
|
+
bundle exec rake erd exclude_attributes="BigTable,User.password_digest,User.remember_token"
|
|
102
|
+
|
|
103
|
+
# erd binary (flags require the -- prefix)
|
|
104
|
+
bundle exec erd --exclude_attributes="BigTable,User.password_digest,User.remember_token"
|
|
105
|
+
```
|
|
106
|
+
|
|
80
107
|
You can also customize fonts (useful if the defaults aren't available on your system):
|
|
81
108
|
|
|
82
109
|
```yaml
|
data/lib/rails_erd/cli.rb
CHANGED
|
@@ -72,6 +72,11 @@ Choice.options do
|
|
|
72
72
|
desc "Filter to exclude listed models in diagram."
|
|
73
73
|
end
|
|
74
74
|
|
|
75
|
+
option :exclude_attributes do
|
|
76
|
+
long "--exclude_attributes=MODEL[.ATTRIBUTE],..."
|
|
77
|
+
desc "Hide attributes per model. Use Model to hide all its attributes or Model.attribute to hide one, e.g. BigTable,User.password_digest."
|
|
78
|
+
end
|
|
79
|
+
|
|
75
80
|
option :sort do
|
|
76
81
|
long "--sort=BOOLEAN"
|
|
77
82
|
desc "Sort attribute list alphabetically"
|
data/lib/rails_erd/config.rb
CHANGED
|
@@ -73,6 +73,11 @@ module RailsERD
|
|
|
73
73
|
when :only, :exclude
|
|
74
74
|
Array(value).join(",").split(",").map { |v| v.strip }
|
|
75
75
|
|
|
76
|
+
# nil | { <string> => true | [<string>] }
|
|
77
|
+
when :exclude_attributes
|
|
78
|
+
require "rails_erd/diagram"
|
|
79
|
+
RailsERD::Diagram.normalize_exclude_attributes(value)
|
|
80
|
+
|
|
76
81
|
# true | false
|
|
77
82
|
when :disconnected, :indirect, :inheritance, :markup, :polymorphism,
|
|
78
83
|
:warn, :cluster
|
data/lib/rails_erd/diagram.rb
CHANGED
|
@@ -55,6 +55,14 @@ module RailsERD
|
|
|
55
55
|
# attributes:: Selects which attributes to display. Can be any combination of
|
|
56
56
|
# +:content+, +:primary_keys+, +:foreign_keys+, +:timestamps+, or
|
|
57
57
|
# +:inheritance+.
|
|
58
|
+
# exclude_attributes:: Hides attributes on a per-model basis, without affecting
|
|
59
|
+
# other models. Accepts a hash that maps model names to
|
|
60
|
+
# either +true+ (hide all attributes for that model) or a
|
|
61
|
+
# list of attribute names to hide. From the command line it
|
|
62
|
+
# can also be given as a comma separated string where each
|
|
63
|
+
# entry is either +Model+ (hide all attributes) or
|
|
64
|
+
# +Model.attribute+ (hide a single attribute), for example
|
|
65
|
+
# <tt>exclude_attributes="BigTable,User.password_digest"</tt>.
|
|
58
66
|
# disconnected:: Set to +false+ to exclude entities that are not connected to other
|
|
59
67
|
# entities. Defaults to +false+.
|
|
60
68
|
# indirect:: Set to +false+ to exclude relationships that are indirect.
|
|
@@ -76,6 +84,38 @@ module RailsERD
|
|
|
76
84
|
new(Domain.generate(options), options).create
|
|
77
85
|
end
|
|
78
86
|
|
|
87
|
+
# Canonicalises the +exclude_attributes+ option into a hash that maps
|
|
88
|
+
# model names (as strings) to either +true+ (hide all attributes) or an
|
|
89
|
+
# array of attribute names to hide. Accepts several input shapes:
|
|
90
|
+
#
|
|
91
|
+
# * a hash, e.g. <tt>{ "BigTable" => true, "User" => ["password_digest"] }</tt>
|
|
92
|
+
# (values may be +true+/+"all"+ to hide every attribute, +false+/+nil+
|
|
93
|
+
# to hide none, or a comma separated string / array of names);
|
|
94
|
+
# * a string or array of <tt>Model</tt> / <tt>Model.attribute</tt>
|
|
95
|
+
# entries, e.g. <tt>"BigTable,User.password_digest"</tt>.
|
|
96
|
+
def normalize_exclude_attributes(value)
|
|
97
|
+
return {} if value.nil? || value == false
|
|
98
|
+
|
|
99
|
+
if value.is_a?(Hash)
|
|
100
|
+
value.each_with_object({}) do |(model, attrs), result|
|
|
101
|
+
result[model.to_s] = normalize_exclude_attribute_value(attrs)
|
|
102
|
+
end
|
|
103
|
+
else
|
|
104
|
+
entries = Array(value).flat_map { |entry| entry.to_s.split(",") }
|
|
105
|
+
entries.each_with_object({}) do |entry, result|
|
|
106
|
+
model, attribute = entry.split(".", 2)
|
|
107
|
+
model = model.to_s.strip
|
|
108
|
+
next if model.empty?
|
|
109
|
+
|
|
110
|
+
if attribute.nil?
|
|
111
|
+
result[model] = true
|
|
112
|
+
elsif result[model] != true
|
|
113
|
+
(result[model] ||= []) << attribute.strip
|
|
114
|
+
end
|
|
115
|
+
end
|
|
116
|
+
end
|
|
117
|
+
end
|
|
118
|
+
|
|
79
119
|
protected
|
|
80
120
|
|
|
81
121
|
def setup(&block)
|
|
@@ -103,6 +143,16 @@ module RailsERD
|
|
|
103
143
|
def callbacks
|
|
104
144
|
@callbacks ||= Hash.new { proc {} }
|
|
105
145
|
end
|
|
146
|
+
|
|
147
|
+
def normalize_exclude_attribute_value(attrs)
|
|
148
|
+
case attrs
|
|
149
|
+
when true then true
|
|
150
|
+
when false, nil then []
|
|
151
|
+
when "all", :all, "true" then true
|
|
152
|
+
else
|
|
153
|
+
Array(attrs).flat_map { |attr| attr.to_s.split(",") }.map(&:strip).reject(&:empty?)
|
|
154
|
+
end
|
|
155
|
+
end
|
|
106
156
|
end
|
|
107
157
|
|
|
108
158
|
# The options that are used to create this diagram.
|
|
@@ -205,13 +255,31 @@ module RailsERD
|
|
|
205
255
|
end
|
|
206
256
|
|
|
207
257
|
def filtered_attributes(entity)
|
|
258
|
+
excluded = excluded_attributes_for(entity)
|
|
259
|
+
return [] if excluded == :all
|
|
260
|
+
|
|
208
261
|
entity.attributes.reject { |attribute|
|
|
262
|
+
# Hide attributes excluded for this specific model.
|
|
263
|
+
excluded.include?(attribute.name) or
|
|
209
264
|
# Select attributes that satisfy the conditions in the :attributes option.
|
|
210
265
|
!options.attributes or entity.specialized? or
|
|
211
266
|
[*options.attributes].none? { |type| attribute.send(:"#{type.to_s.chomp('s')}?") }
|
|
212
267
|
}
|
|
213
268
|
end
|
|
214
269
|
|
|
270
|
+
# Returns the attribute exclusions configured for the given entity through
|
|
271
|
+
# the +exclude_attributes+ option. Returns +:all+ when every attribute
|
|
272
|
+
# should be hidden, or an array of attribute names otherwise.
|
|
273
|
+
def excluded_attributes_for(entity)
|
|
274
|
+
spec = normalized_exclude_attributes[entity.name]
|
|
275
|
+
return :all if spec == true
|
|
276
|
+
Array(spec)
|
|
277
|
+
end
|
|
278
|
+
|
|
279
|
+
def normalized_exclude_attributes
|
|
280
|
+
@normalized_exclude_attributes ||= self.class.normalize_exclude_attributes(options.exclude_attributes)
|
|
281
|
+
end
|
|
282
|
+
|
|
215
283
|
def warn(message)
|
|
216
284
|
puts "Warning: #{message}" if options.warn
|
|
217
285
|
end
|
data/lib/rails_erd/domain.rb
CHANGED
|
@@ -210,11 +210,13 @@ module RailsERD
|
|
|
210
210
|
excluded_names = [options.exclude].flatten.map(&:to_sym)
|
|
211
211
|
|
|
212
212
|
# Suppress warning if either the source model or target model is excluded
|
|
213
|
-
excluded_names.include?(association.active_record.name.to_sym)
|
|
214
|
-
|
|
213
|
+
return true if excluded_names.include?(association.active_record.name.to_sym)
|
|
214
|
+
|
|
215
|
+
target_name = association.options[:polymorphic] ? association.class_name : association.klass.name
|
|
216
|
+
target_name && excluded_names.include?(target_name.to_sym)
|
|
215
217
|
rescue NameError
|
|
216
|
-
# If we can't determine the target class,
|
|
217
|
-
|
|
218
|
+
# If we can't determine the target class, the source model was already checked above
|
|
219
|
+
false
|
|
218
220
|
end
|
|
219
221
|
|
|
220
222
|
def check_polymorphic_association_validity(association)
|
data/lib/rails_erd/version.rb
CHANGED
data/lib/rails_erd.rb
CHANGED
data/test/unit/config_test.rb
CHANGED
|
@@ -122,6 +122,17 @@ class ConfigTest < ActiveSupport::TestCase
|
|
|
122
122
|
assert_equal [:content, :primary_keys], normalize_value(:attributes, ["content", "primary_keys"])
|
|
123
123
|
end
|
|
124
124
|
|
|
125
|
+
test "normalize_value should canonicalize a hash when key is :exclude_attributes." do
|
|
126
|
+
value = { "BigTable" => true, "User" => ["password_digest"] }
|
|
127
|
+
expected = { "BigTable" => true, "User" => ["password_digest"] }
|
|
128
|
+
assert_equal expected, normalize_value(:exclude_attributes, value)
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
test "normalize_value should parse a string when key is :exclude_attributes." do
|
|
132
|
+
expected = { "BigTable" => true, "User" => ["password_digest"] }
|
|
133
|
+
assert_equal expected, normalize_value(:exclude_attributes, "BigTable,User.password_digest")
|
|
134
|
+
end
|
|
135
|
+
|
|
125
136
|
test "normalize_value should return hash with symbol keys when key is :fonts and value is a hash." do
|
|
126
137
|
fonts_value = { "normal" => "Arial", "bold" => "Arial Bold", "italic" => "Arial Italic" }
|
|
127
138
|
expected = {:normal => "Arial", :bold => "Arial Bold", :italic => "Arial Italic"}
|
data/test/unit/diagram_test.rb
CHANGED
|
@@ -358,4 +358,34 @@ class DiagramTest < ActiveSupport::TestCase
|
|
|
358
358
|
Object.const_set :Whisky, Class.new(Beverage)
|
|
359
359
|
assert_equal [], retrieve_attribute_lists(:inheritance => true)[Whisky].map(&:name)
|
|
360
360
|
end
|
|
361
|
+
|
|
362
|
+
test "generate should hide all attributes for a model excluded with true" do
|
|
363
|
+
create_model "Book", :title => :string, :pages => :integer
|
|
364
|
+
create_model "Author", :name => :string
|
|
365
|
+
attribute_lists = retrieve_attribute_lists(:exclude_attributes => { "Book" => true })
|
|
366
|
+
assert_equal [], attribute_lists[Book].map(&:name)
|
|
367
|
+
assert_equal %w{name}, attribute_lists[Author].map(&:name)
|
|
368
|
+
end
|
|
369
|
+
|
|
370
|
+
test "generate should hide only listed attributes for a model" do
|
|
371
|
+
create_model "Book", :title => :string, :subtitle => :string, :pages => :integer
|
|
372
|
+
attribute_lists = retrieve_attribute_lists(:exclude_attributes => { "Book" => ["subtitle"] })
|
|
373
|
+
assert_equal %w{pages title}, attribute_lists[Book].map(&:name).sort
|
|
374
|
+
end
|
|
375
|
+
|
|
376
|
+
test "generate should hide attributes for the listed model only" do
|
|
377
|
+
create_model "Book", :title => :string
|
|
378
|
+
create_model "Author", :name => :string
|
|
379
|
+
attribute_lists = retrieve_attribute_lists(:exclude_attributes => { "Book" => ["title"] })
|
|
380
|
+
assert_equal [], attribute_lists[Book].map(&:name)
|
|
381
|
+
assert_equal %w{name}, attribute_lists[Author].map(&:name)
|
|
382
|
+
end
|
|
383
|
+
|
|
384
|
+
test "generate should accept exclude_attributes as a string" do
|
|
385
|
+
create_model "Book", :title => :string, :subtitle => :string
|
|
386
|
+
create_model "Author", :name => :string
|
|
387
|
+
attribute_lists = retrieve_attribute_lists(:exclude_attributes => "Book.subtitle,Author")
|
|
388
|
+
assert_equal %w{title}, attribute_lists[Book].map(&:name)
|
|
389
|
+
assert_equal [], attribute_lists[Author].map(&:name)
|
|
390
|
+
end
|
|
361
391
|
end
|
data/test/unit/domain_test.rb
CHANGED
|
@@ -255,6 +255,19 @@ class DomainTest < ActiveSupport::TestCase
|
|
|
255
255
|
assert_match(/polymorphic interface FooBar does not exist/, output)
|
|
256
256
|
end
|
|
257
257
|
|
|
258
|
+
test "relationships should not crash when exclude is present and a polymorphic association's interface does not exist" do
|
|
259
|
+
create_model "Foo" do
|
|
260
|
+
has_many :bars, :as => :foo
|
|
261
|
+
end
|
|
262
|
+
create_model "Bar", :foobar => :references do
|
|
263
|
+
belongs_to :foo_bar, :polymorphic => true
|
|
264
|
+
end
|
|
265
|
+
output = collect_stdout do
|
|
266
|
+
Domain.generate(:exclude => ["Qux"]).relationships
|
|
267
|
+
end
|
|
268
|
+
assert_match(/polymorphic interface FooBar does not exist/, output)
|
|
269
|
+
end
|
|
270
|
+
|
|
258
271
|
test "relationships should not warn when a bad association is encountered if warnings are disabled" do
|
|
259
272
|
create_model "Foo" do
|
|
260
273
|
has_many :flabs
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: rails-erd
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 2.0.
|
|
4
|
+
version: 2.0.2
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Rolf Timmermans
|
|
@@ -178,7 +178,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
|
178
178
|
- !ruby/object:Gem::Version
|
|
179
179
|
version: '0'
|
|
180
180
|
requirements: []
|
|
181
|
-
rubygems_version: 4.0.
|
|
181
|
+
rubygems_version: 4.0.13
|
|
182
182
|
specification_version: 4
|
|
183
183
|
summary: Entity-relationship diagram for your Rails models.
|
|
184
184
|
test_files:
|