Class: RailsERD::Diagram
- Inherits:
-
Object
- Object
- RailsERD::Diagram
- Defined in:
- lib/rails_erd/diagram.rb,
lib/rails_erd/diagram/mermaid.rb,
lib/rails_erd/diagram/graphviz.rb
Overview
This class is an abstract class that will process a domain model and allows easy creation of diagrams. To implement a new diagram type, derive from this class and override process_entity
, process_relationship
, and (optionally) save
.
As an example, a diagram class that generates code that can be used with yUML (yuml.me) can be as simple as:
require "rails_erd/diagram"
class YumlDiagram < RailsERD::Diagram
setup { @edges = [] }
each_relationship do |relationship|
return if relationship.indirect?
arrow = case
when relationship.one_to_one? then "1-1>"
when relationship.one_to_many? then "1-*>"
when relationship.many_to_many? then "*-*>"
end
@edges << "[#{relationship.source}] #{arrow} [#{relationship.destination}]"
end
save { @edges * "\n" }
end
Then, to generate the diagram (example based on the domain model of Gemcutter):
YumlDiagram.create
#=> "[Rubygem] 1-*> [Ownership]
# [Rubygem] 1-*> [Subscription]
# [Rubygem] 1-*> [Version]
# [Rubygem] 1-1> [Linkset]
# [Rubygem] 1-*> [Dependency]
# [Version] 1-*> [Dependency]
# [User] 1-*> [Ownership]
# [User] 1-*> [Subscription]
# [User] 1-*> [WebHook]"
For another example implementation, see Diagram::Graphviz, which is the default (and currently only) diagram type that is used by Rails ERD.
Options
The following options are available and will by automatically used by any diagram generator inheriting from this class.
- attributes
-
Selects which attributes to display. Can be any combination of
:content
,:primary_keys
,:foreign_keys
,:timestamps
, or:inheritance
. - disconnected
-
Set to
false
to exclude entities that are not connected to other entities. Defaults tofalse
. - indirect
-
Set to
false
to exclude relationships that are indirect. Indirect relationships are defined in Active Record withhas_many :through
associations. - inheritance
-
Set to
true
to include specializations, which correspond to Rails single table inheritance. - polymorphism
-
Set to
true
to include generalizations, which correspond to Rails polymorphic associations. - warn
-
When set to
false
, no warnings are printed to the command line while processing the domain model. Defaults totrue
.
Defined Under Namespace
Instance Attribute Summary collapse
-
#domain ⇒ Object
readonly
The domain that this diagram represents.
-
#options ⇒ Object
readonly
The options that are used to create this diagram.
Class Method Summary collapse
-
.create(options = {}) ⇒ Object
Generates a new domain model based on all
ActiveRecord::Base
subclasses, and creates a new diagram.
Instance Method Summary collapse
-
#create ⇒ Object
Generates and saves the diagram, returning the result of
save
. -
#generate ⇒ Object
Generates the diagram, but does not save the output.
-
#initialize(domain, options = {}) ⇒ Diagram
constructor
Create a new diagram based on the given domain.
- #recurse_into_relationships(entity, max_level, current_level = 0) ⇒ Object
- #save ⇒ Object
Constructor Details
Instance Attribute Details
#domain ⇒ Object (readonly)
The domain that this diagram represents.
110 111 112 |
# File 'lib/rails_erd/diagram.rb', line 110 def domain @domain end |
#options ⇒ Object (readonly)
The options that are used to create this diagram.
107 108 109 |
# File 'lib/rails_erd/diagram.rb', line 107 def @options end |
Class Method Details
.create(options = {}) ⇒ Object
Generates a new domain model based on all ActiveRecord::Base
subclasses, and creates a new diagram. Use the given options for both the domain generation and the diagram generation.
73 74 75 |
# File 'lib/rails_erd/diagram.rb', line 73 def create( = {}) new(Domain.generate(), ).create end |
Instance Method Details
#create ⇒ Object
Generates and saves the diagram, returning the result of save
.
118 119 120 121 |
# File 'lib/rails_erd/diagram.rb', line 118 def create generate save end |
#generate ⇒ Object
Generates the diagram, but does not save the output. It is called internally by Diagram#create.
125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 |
# File 'lib/rails_erd/diagram.rb', line 125 def generate instance_eval(&callbacks[:setup]) if .only_recursion_depth.present? depth = .only_recursion_depth.to_s.to_i [:only].dup.each do |class_name| [:only]+= recurse_into_relationships(@domain.entity_by_name(class_name), depth) end [:only].uniq! end filtered_entities.each do |entity| instance_exec entity, filtered_attributes(entity), &callbacks[:each_entity] end filtered_specializations.each do |specialization| instance_exec specialization, &callbacks[:each_specialization] end filtered_relationships.each do |relationship| instance_exec relationship, &callbacks[:each_relationship] end end |
#recurse_into_relationships(entity, max_level, current_level = 0) ⇒ Object
148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 |
# File 'lib/rails_erd/diagram.rb', line 148 def recurse_into_relationships(entity, max_level, current_level = 0) return [] unless entity return [] if max_level == current_level relationships = entity.relationships.reject{|r| r.indirect? || r.recursive?} relationships.map do |relationship| other_entitiy = if relationship.source == entity relationship.destination else relationship.source end if other_entitiy and !other_entitiy.generalized? [other_entitiy.name] + recurse_into_relationships(other_entitiy, max_level, current_level + 1) else [] end end.flatten.uniq end |
#save ⇒ Object
168 169 170 |
# File 'lib/rails_erd/diagram.rb', line 168 def save instance_eval(&callbacks[:save]) end |