Skip to content

Instantly share code, notes, and snippets.

@QuantumGhost
Last active September 21, 2024 19:19
Show Gist options
  • Save QuantumGhost/0955a45383a0b6c0bc24f9654b3cb561 to your computer and use it in GitHub Desktop.
Save QuantumGhost/0955a45383a0b6c0bc24f9654b3cb561 to your computer and use it in GitHub Desktop.
A simple template for PlantUML to draw ER diagram.The basic idea comes from http://plantuml.sourceforge.net/qa/?qa=331/database-modeling
@startuml
' uncomment the line below if you're using computer with a retina display
' skinparam dpi 300
!define Table(name,desc) class name as "desc" << (T,#FFAAAA) >>
' we use bold for primary key
' green color for unique
' and underscore for not_null
!define primary_key(x) <b>x</b>
!define unique(x) <color:green>x</color>
!define not_null(x) <u>x</u>
' other tags available:
' <i></i>
' <back:COLOR></color>, where color is a color name or html color code
' (#FFAACC)
' see: http://plantuml.com/classes.html#More
hide methods
hide stereotypes
' entities
Table(user, "user\n(User in our system)") {
primary_key(id) INTEGER
not_null(unique(username)) VARCHAR[32]
not_null(password) VARCHAR[64]
}
Table(session, "session\n(session for user)") {
primary_key(id) INTEGER
not_null(user_id) INTEGER
not_null(unique(session_id)) VARCHAR[64]
}
Table(user_profile, "user_profile\n(Some info of user)") {
primary_key(user_id) INTEGER
age SMALLINT
gender SMALLINT
birthday DATETIME
}
Table(group, "group\n(group of users)") {
primary_key(id) INTEGER
not_null(name) VARCHAR[32]
}
Table(user_group, "user_group\n(relationship of user and group)") {
primary_key(user_id) INTEGER
primary_key(group_id) INTEGER
joined_at DATETIME
}
' relationships
' one-to-one relationship
user -- user_profile : "A user only \nhas one profile"
' one to may relationship
user --> session : "A user may have\n many sessions"
' many to many relationship
' Add mark if you like
user "1" --> "*" user_group : "A user may be \nin many groups"
group "1" --> "0..N" user_group : "A group may \ncontain many users"
@enduml
Display the source blob
Display the rendered blob
Raw
<?xml version="1.0" encoding="UTF-8" standalone="yes"?><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" height="467.2px" style="width:1008px;height:467px;" version="1.1" viewBox="0 0 1008 467" width="1008px"><defs><filter height="300%" id="f1" width="300%" x="-1" y="-1"><feGaussianBlur result="blurOut" stdDeviation="3.200000047683716"/><feColorMatrix in="blurOut" result="blurOut2" type="matrix" values="0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 .4 0"/><feOffset dx="6.400000095367432" dy="6.400000095367432" in="blurOut2" result="blurOut3"/><feBlend in="SourceGraphic" in2="blurOut3" mode="normal"/></filter></defs><g><rect fill="#FEFECE" filter="url(#f1)" height="136.2094" style="stroke: #A80036; stroke-width: 2.400000035762787;" width="235.2" x="270.4" y="12.8"/><ellipse cx="294.4" cy="43.4125" fill="#FFAAAA" rx="17.6" ry="17.6" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><path d="M295.7469,54.2125 L291.8289,54.2125 L291.8289,37.8102 L286.7953,37.8102 L286.7953,34.3836 L300.7805,34.3836 L300.7805,37.8102 L295.7469,37.8102 Z "/><text fill="#000000" font-family="sans-serif" font-size="19.2" lengthAdjust="spacingAndGlyphs" textLength="40" x="388.8" y="39.3625">user</text><text fill="#000000" font-family="sans-serif" font-size="19.2" lengthAdjust="spacingAndGlyphs" textLength="184" x="316.8" y="61.975">(User in our system)</text><line style="stroke: #A80036; stroke-width: 2.400000035762787;" x1="272" x2="504" y1="74.025" y2="74.025"/><text fill="#000000" font-family="sans-serif" font-size="17.6" font-weight="bold" lengthAdjust="spacingAndGlyphs" textLength="17.6" x="280" y="97.4406">id</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="72" x="302.4" y="97.4406">INTEGER</text><text fill="#008000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" text-decoration="underline" textLength="84.8" x="280" y="118.1688">username</text><line style="stroke: #008000; stroke-width: 1.0;" x1="280" x2="364.8" y1="121.3688" y2="121.3688"/><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="120" x="369.6" y="118.1688">VARCHAR[32]</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" text-decoration="underline" textLength="83.2" x="280" y="138.8969">password</text><line style="stroke: #000000; stroke-width: 1.0;" x1="280" x2="363.2" y1="142.0969" y2="142.0969"/><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="120" x="368" y="138.8969">VARCHAR[64]</text><rect fill="#FEFECE" filter="url(#f1)" height="115.4813" style="stroke: #A80036; stroke-width: 2.400000035762787;" width="209.6" x="9.6" y="316.8"/><ellipse cx="33.6" cy="347.4125" fill="#FFAAAA" rx="17.6" ry="17.6" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><path d="M34.9469,358.2125 L31.0289,358.2125 L31.0289,341.8102 L25.9953,341.8102 L25.9953,338.3836 L39.9805,338.3836 L39.9805,341.8102 L34.9469,341.8102 Z "/><text fill="#000000" font-family="sans-serif" font-size="19.2" lengthAdjust="spacingAndGlyphs" textLength="67.2" x="101.6" y="343.3625">session</text><text fill="#000000" font-family="sans-serif" font-size="19.2" lengthAdjust="spacingAndGlyphs" textLength="158.4" x="56" y="365.975">(session for user)</text><line style="stroke: #A80036; stroke-width: 2.400000035762787;" x1="11.2" x2="217.6" y1="378.025" y2="378.025"/><text fill="#000000" font-family="sans-serif" font-size="17.6" font-weight="bold" lengthAdjust="spacingAndGlyphs" textLength="17.6" x="19.2" y="401.4406">id</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="72" x="41.6" y="401.4406">INTEGER</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" text-decoration="underline" textLength="64" x="19.2" y="422.1688">user_id</text><line style="stroke: #000000; stroke-width: 1.0;" x1="19.2" x2="83.2" y1="425.3688" y2="425.3688"/><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="72" x="88" y="422.1688">INTEGER</text><rect fill="#FEFECE" filter="url(#f1)" height="156.9375" style="stroke: #A80036; stroke-width: 2.400000035762787;" width="224" x="276" y="296"/><ellipse cx="300" cy="326.6125" fill="#FFAAAA" rx="17.6" ry="17.6" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><path d="M301.3469,337.4125 L297.4289,337.4125 L297.4289,321.0102 L292.3953,321.0102 L292.3953,317.5836 L306.3805,317.5836 L306.3805,321.0102 L301.3469,321.0102 Z "/><text fill="#000000" font-family="sans-serif" font-size="19.2" lengthAdjust="spacingAndGlyphs" textLength="108.8" x="354.4" y="322.5625">user_profile</text><text fill="#000000" font-family="sans-serif" font-size="19.2" lengthAdjust="spacingAndGlyphs" textLength="172.8" x="322.4" y="345.175">(Some info of user)</text><line style="stroke: #A80036; stroke-width: 2.400000035762787;" x1="277.6" x2="498.4" y1="357.225" y2="357.225"/><text fill="#000000" font-family="sans-serif" font-size="17.6" font-weight="bold" lengthAdjust="spacingAndGlyphs" textLength="65.6" x="285.6" y="380.6406">user_id</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="72" x="356" y="380.6406">INTEGER</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="120" x="285.6" y="401.3688">age SMALLINT</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="150.4" x="285.6" y="422.0969">gender SMALLINT</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="163.2" x="285.6" y="442.825">birthday DATETIME</text><rect fill="#FEFECE" filter="url(#f1)" height="115.4813" style="stroke: #A80036; stroke-width: 2.400000035762787;" width="198.4" x="730.4" y="23.2"/><ellipse cx="754.4" cy="53.8125" fill="#FFAAAA" rx="17.6" ry="17.6" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><path d="M755.7469,64.6125 L751.8289,64.6125 L751.8289,48.2102 L746.7953,48.2102 L746.7953,44.7836 L760.7805,44.7836 L760.7805,48.2102 L755.7469,48.2102 Z "/><text fill="#000000" font-family="sans-serif" font-size="19.2" lengthAdjust="spacingAndGlyphs" textLength="54.4" x="823.2" y="49.7625">group</text><text fill="#000000" font-family="sans-serif" font-size="19.2" lengthAdjust="spacingAndGlyphs" textLength="147.2" x="776.8" y="72.375">(group of users)</text><line style="stroke: #A80036; stroke-width: 2.400000035762787;" x1="732" x2="927.2" y1="84.425" y2="84.425"/><text fill="#000000" font-family="sans-serif" font-size="17.6" font-weight="bold" lengthAdjust="spacingAndGlyphs" textLength="17.6" x="740" y="107.8406">id</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="72" x="762.4" y="107.8406">INTEGER</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" text-decoration="underline" textLength="46.4" x="740" y="128.5688">name</text><line style="stroke: #000000; stroke-width: 1.0;" x1="740" x2="786.4" y1="131.7688" y2="131.7688"/><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="120" x="791.2" y="128.5688">VARCHAR[32]</text><rect fill="#FEFECE" filter="url(#f1)" height="136.2094" style="stroke: #A80036; stroke-width: 2.400000035762787;" width="344" x="606.4" y="306.4"/><ellipse cx="630.4" cy="337.0125" fill="#FFAAAA" rx="17.6" ry="17.6" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><path d="M631.7469,347.8125 L627.8289,347.8125 L627.8289,331.4102 L622.7953,331.4102 L622.7953,327.9836 L636.7805,327.9836 L636.7805,331.4102 L631.7469,331.4102 Z "/><text fill="#000000" font-family="sans-serif" font-size="19.2" lengthAdjust="spacingAndGlyphs" textLength="104" x="747.2" y="332.9625">user_group</text><text fill="#000000" font-family="sans-serif" font-size="19.2" lengthAdjust="spacingAndGlyphs" textLength="292.8" x="652.8" y="355.575">(relationship of user and group)</text><line style="stroke: #A80036; stroke-width: 2.400000035762787;" x1="608" x2="948.8" y1="367.625" y2="367.625"/><text fill="#000000" font-family="sans-serif" font-size="17.6" font-weight="bold" lengthAdjust="spacingAndGlyphs" textLength="65.6" x="616" y="391.0406">user_id</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="72" x="686.4" y="391.0406">INTEGER</text><text fill="#000000" font-family="sans-serif" font-size="17.6" font-weight="bold" lengthAdjust="spacingAndGlyphs" textLength="80" x="616" y="411.7688">group_id</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="72" x="700.8" y="411.7688">INTEGER</text><text fill="#000000" font-family="sans-serif" font-size="17.6" lengthAdjust="spacingAndGlyphs" textLength="169.6" x="616" y="432.4969">joined_at DATETIME</text><path d="M384.736,148.928 C384.0976,164.6224 383.5248,181.2976 383.2,196.8 C382.52,229.1936 383.2272,264.936 384.288,295.7005 " fill="none" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="113.6" x="400" y="218.5094">A user only</text><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="150.4" x="384.8" y="243.0063">has one profile</text><path d="M270.08,141.3728 C245.7472,157.1184 221.6912,175.7168 202.4,196.8 C172.904,229.0368 150.9152,272.9936 136.2947,308.9134 " fill="none" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><polygon fill="#A80036" points="133.2867,316.4491,144.5693,305.4481,136.2526,309.0192,132.6815,300.7026,133.2867,316.4491" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="164.8" x="204" y="218.5094">A user may have</text><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="148.8" x="215.2" y="243.0063">many sessions</text><path d="M478.3552,148.832 C499.6432,164.5312 522.24,181.232 543.2,196.8 C589.2544,231.0032 640.2448,269.128 682.9424,301.1256 " fill="none" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><polygon fill="#A80036" points="689.7216,306.2069,682.0368,292.4496,683.3199,301.4091,674.3604,302.6922,689.7216,306.2069" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="142.4" x="614.4" y="218.5094">A user may be</text><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="156.8" x="610.4" y="243.0063">in many groups</text><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="12.8" x="478.9356" y="181.7194">1</text><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="9.6" x="664.6392" y="289.0575">*</text><path d="M819.6064,139.0816 C811.6288,184.3312 800.3808,248.1296 791.6512,297.6395 " fill="none" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><polygon fill="#A80036" points="790.1632,306.0824,798.9668,293.0127,791.5526,298.204,786.3613,290.7897,790.1632,306.0824" style="stroke: #A80036; stroke-width: 1.600000023841858;"/><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="128" x="841.6" y="218.5094">A group may</text><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="196.8" x="810.4" y="243.0063">contain many users</text><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="12.8" x="803.8863" y="171.7291">1</text><text fill="#000000" font-family="sans-serif" font-size="20.8" lengthAdjust="spacingAndGlyphs" textLength="41.6" x="747.123" y="289.415">0..N</text></g></svg>
@startuml
' uncomment the line below if you're using computer with a retina display
' skinparam dpi 300
!define Table(name,desc) class name as "desc" << (T,#FFAAAA) >>
' we use bold for primary key
' green color for unique
' and underscore for not_null
!define primary_key(x) <b>x</b>
!define unique(x) <color:green>x</color>
!define not_null(x) <u>x</u>
' other tags available:
' <i></i>
' <back:COLOR></color>, where color is a color name or html color code
' (#FFAACC)
' see: http://plantuml.com/classes.html#More
hide methods
hide stereotypes
' entities
' relationships
@enduml
@tim-rohrer
Copy link

tim-rohrer commented Dec 3, 2017

Nice!

I'm researching, but is there a way to add lengths to the field types? For example, CHAR(2)? I realize could do something like CHAR-2, but it would be nice to put them in parens.

Also, I'm experimenting with foreign keys...

@Potherca
Copy link

Potherca commented Mar 9, 2018

@tim-rohrer You could use:

!define VARCHAR(x) <color:gray>VARCHAR(x)</color>

@olgapshen
Copy link

olgapshen commented Mar 22, 2018

if "desc" - will omit quotes it will break NetBeans plugin, but if descriptions in Tables will omit quotes it will works both on CLI and NetBeans.
https://stackoverflow.com/questions/49423335/sintax-error-in-plantuml

@ityoung
Copy link

ityoung commented Feb 18, 2019

Nice work!

@NewAlexandria
Copy link

You can show one-to-many relations using the more-common 'bird foot' line notation, supported in plantUML now:

user "1" *--+ "many" user_group : has many groups through >

@QuantumGhost
Copy link
Author

You can show one-to-many relations using the more-common 'bird foot' line notation, supported in plantUML now:

user "1" *--+ "many" user_group : has many groups through >

Nice!

@pavelvrublevskij
Copy link

pavelvrublevskij commented Oct 7, 2019

Please fix 30 line:
not_null(unique(session_id) VARCHAR[64]
to
not_null(unique(session_id)) VARCHAR[64]

@QuantumGhost
Copy link
Author

@pavelvrublevskij Fixed. Thanks for mentioning.

@xinyifly
Copy link

Have you gave Information Engineering notation a try? https://plantuml.com/ie-diagram

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment