導入
雨がすごく続いていて、ノアの箱舟の40日間連続雨が他人事に思えなくなってきたむらのです。
最近DBの違いを耳にして、正直何が違うか全くわかっていないため、少し調べました、、、
まだ全然覚えられていないのですが、結構な違いがありました。
特に「スキーマ」という言葉、DBの種類によって指しているものが結構違うことが分かりました。
「MySQLはスキーマがない」と耳にして、驚いて調べたら正確には違う(安心)ようで、各DBでの位置づけを端的に整理してみます。
結論(先に一言で)
| DB | スキーマの位置づけ |
|---|---|
| MySQL | スキーマ ≒ データベース(同義語) |
| PostgreSQL | スキーマ = DB内の名前空間(1DB内に複数スキーマ) |
| SQL Server |
スキーマ = DB内の名前空間(デフォルトはdbo) |
| Oracle | スキーマ ≒ ユーザー(1ユーザー = 1スキーマ) |
つまり「スキーマがない」わけではなく、MySQLだけ「スキーマ=DB」という特殊な扱いをしている、というのが正確な理解です。
各DBの詳細
MySQL:スキーマ ≒ データベース
MySQL公式グロッサリーでは、物理的にスキーマとデータベースは同義語であり、CREATE DATABASEの代わりにCREATE SCHEMAを使うことができるとされています。1
実際に以下の2文は完全に同じ動作をします。
CREATE DATABASE app_data;
CREATE SCHEMA app_data;
つまり sales.users と書いたとき、これは「salesという名前のデータベース内のusersテーブル」を意味します。
PostgreSQL:スキーマ = DB内の名前空間
PostgreSQL公式ドキュメントでは、1つのデータベースが複数の名前付きスキーマを持ち、それぞれのスキーマがテーブルなどのオブジェクトを含むとされています。2
DB: company
├─ schema: sales → sales.users
└─ schema: hr → hr.users
同じDB内で sales.users と hr.users が名前空間として共存できます。
SQL Server:スキーマ = DB内の名前空間(PostgreSQLに近い)
Microsoft公式ドキュメントでは、スキーマはデータベースオブジェクトの名前付きコンテナであり、オブジェクトを別々の名前空間にグループ化できるとされ、AdventureWorksサンプルDBにはProduction・Sales・HumanResourcesといったスキーマが含まれる例が示されています。3
デフォルトスキーマは dbo(database owner)で、新規作成されたデータベースでは自動的にこのスキーマが使われます。4
4部構成の命名規則も存在します。
Server.Database.Schema.Object
Oracle:スキーマ ≒ ユーザー
Oracleではスキーマを扱うことがSQL Serverでデータベースを扱うこととほぼ同じ感覚であり、ユーザーはOracleサーバーに接続して、SQL Serverでデータベースを操作するのと同じようにスキーマを操作するとされています。5
一般的に「Oracleの1ユーザー = 1スキーマ」という理解と一致します。
まとめ
- MySQLだけ「スキーマ=DB」という特殊なルールを持つ
- PostgreSQL・SQL Serverは「1つのDBの中に複数スキーマ」という同じ考え方
- Oracleは「スキーマ=ユーザー単位」という別の考え方
正直「スキーマ」という同じ単語なのにDBごとに指すものが違うとは思っていなかったので、調べてみて良かったです。
雨も40日連続とはいかないと思いますが、しばらくは家で大人しく勉強していようと思います。
まだ覚えられていない部分も多いので、また新しい発見があれば記事にしていきます。