LoginSignup
2

Railsで作ったシステムのER図を日本語で出してほしいと言われたときにやったこと

Posted at

Ruby on Railsを使った開発をしていると「システムのER図が欲しい」といったお願いされることがあります。

Railsを使っているのであれば、rails-erd というRubyGemを使うことで簡単にER図を出力できます。

rails-erdで出力されるER図はEntityもAttributeも全て英語です。

erd.png

提出先がエンジニアである場合や、普段からモデル名を使ったコミュニケーションをしている場合であればこのままでもなんとかなるかもしれません。

一方、相手がビジネスサイドのメンバーである場合や、普段はモデルを日本語変換してコミュニケーションしている相手の場合はこのER図をそのまま出しても困惑されてしまいます。

そこで、今回はなんとかしてEntity・Attributeを日本語化できないか検討しました。結論とそこに至った過程をメモしておきます。

結論

結論としては、rails-erd の下記ファイルを直接編集することで日本語化することができました。

erd.png

Railsのi18nに対応して、モデル名やカラム名の日本語化に対応していることが前提ですのでご注意ください。

変更ファイル

変更点

 <% if options.orientation == :horizontal %>{<% end %>
 <table border="0" align="center" cellspacing="0.5" cellpadding="0" width="<%= NODE_WIDTH + 4 %>">
-  <tr><td align="center" valign="bottom" width="<%= NODE_WIDTH %>"><font face="<%= FONTS[:bold] %>" point-size="11"><%= entity.name %></font></td></tr>
+  <tr><td align="center" valign="bottom" width="<%= NODE_WIDTH %>"><font face="<%= FONTS[:bold] %>" point-size="11"><%= entity.model.model_name.human %></font></td></tr>
 </table>
 <% if attributes.any? %>
 |
 <table border="0" align="left" cellspacing="2" cellpadding="0" width="<%= NODE_WIDTH + 4 %>">
 <%   attributes.each do |attribute| %>
-  <tr><td align="left" width="<%= NODE_WIDTH %>" port="<%= attribute %>"><%= attribute.name %> <font face="<%= FONTS[:italic] %>" color="grey60"><%= attribute.type_description %></font></td></tr>
+  <tr><td align="left" width="<%= NODE_WIDTH %>" port="<%= attribute %>"><%= entity.model.human_attribute_name(attribute.name) %> <font face="<%= FONTS[:italic] %>" color="grey60"><%= attribute.type_description %></font></td></tr>
 <%   end %>
 </table>
 <% else %>

結論に至るまでの過程

rails-erd以外の既存ツールを検討

DBスキーマを出力するツールは rails-erd に限らずいくつか存在します。それらのツールを使うことで簡単に解決ができないか検討しました。

しかし、多くのツールにおいて、日本語化をするためにはDBスキーマの物理名と論理名(日本語)の対応付けを別途行う必要があります。

Railsで作られたアプリであれば大抵の場合、i18nで既に日本語定義を終えているはずなので、日本語のER図を出すためだけに再度対応付けを行うのは避けたいところです。

このため、やはり rails-erd を用いてER図を出力する方向で検討することにしました。

rails-erdにおいてER図のEntity・Attributeに該当する箇所を探す

ファイル名からあたりを付けつつ、適宜 binding.debugger を埋め込んでコマンドを実行してみることで、出力を行っているファイルを見つけ出します。

今回の場合は、前述の通り rails_erd/diagram/templates/node.html.erb というERBファイルにたどり着きました。

ERBファイル内で参照できる変数・その変数メソッドを探る

このERBファイルを読んで、使えそうな変数を見つけます。 entityattribute という変数が存在するので、これらは使えそうということがわかります。

このERBファイル内に <%= binding.debugger %> を埋め込んで、 entityattribute がどのクラスのオブジェクトなのか確認します。

entity.class.name #=> "RailsERD::Domain::Entity"

attributes.class.name #=> "Array"
attributes.first.class.name #=> "RailsERD::Domain::Attribute"

namescopeをたどると、EntityとAttributeは次のファイルに定義されているクラスのインスタンスであることがわかります。

このうち、 entity.rb には model という attr_reader が定義されているので、これがおそらくActiveRecordのインスタンスだろうと推測しました。実際に試してみます。

entity.model #=> ActiveStorage::Attachment(id: integer, name: string, record_type: string, record_id: integer, blob_id: integer, created_at: datetime)

# 何回かcontinueして再度実施
entity.model #=> Announcement(id: integer, title: string, body: text, created_at: datetime, updated_at: datetime)

たまたま最初のクラスが ActiveStorage::Attachment だったので、何回かcontinueすることで entity に入るオブジェクトがActiveRecordのインスタンスとなることを確認できました。

あとはRailsのi18n機能のメソッドを使うことで日本語化できます。

おわりに

今回は、RubyGemの中身を読み解いてソースコードを一部変更することで目的を達成しました。

できればPull Requestを出して、コマンドオプション等で簡単に出力モードを切り替えられるようにできるとより便利なのですが、それは時間のある時に対応したいと思います。

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2