MySQL5.7がGAになって5ヶ月がたちますね。
この記事を書いている時点(2016/3/27)のMySQL最新版は5.7.11なのですが、
このMySQL 5.7.11で、なんと新機能が搭載されました。
5.7.9でGAだったのに、GAリリース後にも新機能が入るとは、、、
と言う話はおいといて、早速試してみましょう。
新機能は、
「InnoDB Tablespace Encryption」
です。
MySQLに格納されているデータは、
ibdataファイル、もしくは、
初期化パラメータ「innodb_file_per_table」がONの場合は、
(テーブル名).ibdファイルという形で
実ファイルで保持されています。
しかし、このファイルは暗号化されていないため、
OS上から直接中身を見ることができます。
(完全な平文ではないですが、要所要所のキーワードは読み取れる、
というような状態です。後で確認します)
これを暗号化しよう、というのが、
このInnoDB Tablespace Encryptionという機能です。
(ちなみに、MySQLでいうTablespaceというのは、
Oracle DatabaseでいうTablespaceとは全く別物ですので注意が必要です)
実際に見たほうが早いと思いますので、早速見ていきましょう。
ここではworldデータベース(MySQL公式サイトで公開されています)を例にとりましょう。
mysql> show create table Country\G *************************** 1. row *************************** Table: Country Create Table: CREATE TABLE `Country` ( `Code` char(3) NOT NULL DEFAULT '', `Name` char(52) NOT NULL DEFAULT '', `Continent` enum('Asia','Europe','North America','Africa','Oceania','Antarctica','South America') NOT NULL DEFAULT 'Asia', `Region` char(26) NOT NULL DEFAULT '', `SurfaceArea` float(10,2) NOT NULL DEFAULT '0.00', `IndepYear` smallint(6) DEFAULT NULL, `Population` int(11) NOT NULL DEFAULT '0', `LifeExpectancy` float(3,1) DEFAULT NULL, `GNP` float(10,2) DEFAULT NULL, `GNPOld` float(10,2) DEFAULT NULL, `LocalName` char(45) NOT NULL DEFAULT '', `GovernmentForm` char(45) NOT NULL DEFAULT '', `HeadOfState` char(60) DEFAULT NULL, `Capital` int(11) DEFAULT NULL, `Code2` char(2) NOT NULL DEFAULT '', PRIMARY KEY (`Code`) ) ENGINE=InnoDB DEFAULT CHARSET=latin1 1 row in set (0.00 sec) mysql> exit [root@mysql57 ~]# [root@mysql57 ~]# head /var/lib/mysql/world/Country.ibd (一部のみ抜粋) Coprincipality 7AD @ANT ,ッ#RNetherlands Antilles Caribbean HDOィffBNederlandse Antillen Nonmetropolitan Territory of The Netherlands Beatrix !ANHARE ,ッ#]United Arab Emirates Middle East H」Gウ%?(33BNG珣Al-Imarat al-エArabiya al-Muttahida Emirate Federation Zayid bin Sultan al-Nahayan AAEPARG ,ッ#hArgentina
こんな具合に、ただの平文ではないにせよ、
中身をみると、NetherlandsとかUnited Arab Emiratesとか、
ところどころ平文が見えてしまいます。
ちなみに、MySQLに習熟している人であれば、
ここで見える平文以上に読み取れる情報はあるそうです。
これを暗号化しましょう。
今回はalter table文を使います。
alter table文は、MySQLでは内部的にテーブルの再作成を行っていますので、
新しいテーブルを作った、
と思って頂ければ良いと思います。
alter table文で、ENCRYPTION=’Y’と足すだけです。
(create table文でも同じです)
mysql> alter table world.Country ENCRYPTION='Y'; Query OK, 239 rows affected (0.06 sec) Records: 239 Duplicates: 0 Warnings: 0 mysql> show create table world.Country\G *************************** 1. row *************************** Table: Country Create Table: CREATE TABLE `Country` ( `Code` char(3) NOT NULL DEFAULT '', `Name` char(52) NOT NULL DEFAULT '', `Continent` enum('Asia','Europe','North America','Africa','Oceania','Antarctica','South America') NOT NULL DEFAULT 'Asia', `Region` char(26) NOT NULL DEFAULT '', `SurfaceArea` float(10,2) NOT NULL DEFAULT '0.00', `IndepYear` smallint(6) DEFAULT NULL, `Population` int(11) NOT NULL DEFAULT '0', `LifeExpectancy` float(3,1) DEFAULT NULL, `GNP` float(10,2) DEFAULT NULL, `GNPOld` float(10,2) DEFAULT NULL, `LocalName` char(45) NOT NULL DEFAULT '', `GovernmentForm` char(45) NOT NULL DEFAULT '', `HeadOfState` char(60) DEFAULT NULL, `Capital` int(11) DEFAULT NULL, `Code2` char(2) NOT NULL DEFAULT '', PRIMARY KEY (`Code`) ) ENGINE=InnoDB DEFAULT CHARSET=latin1 ENCRYPTION='Y' 1 row in set (0.00 sec) mysql>
出力の一番最後に、「ENCRYPTION=’Y’」と出力されている点が、
暗号化なしのshow create table結果と違っていますね。
さあ、.ibdファイルを見てみましょう。
[root@mysql57 ~]# head /var/lib/mysql/world/Country.ibd (一部のみ抜粋) 偂ヨ鉉&8ゥwC・ンモコテJ?]ミ~+ v ュヲコ>"b?o3ス^Z鑼ムh渧イNヒ]Usu・_・]m|ゥ。@、ヤ籠3Iュャ「m3Rョナ゚・7・ャs{。P{アンo聽OC <<ャ朎1iG・メ蠑IZ・・゙\キnアモ==ツ# [ミ・・'ゥ+K$ヤq イ AO・sdc?7・ )/サア}S|?c;+@・ ]コセ}? ciV Vvd-}、 ?サ粫6kエKpク>z| _ネ。鬮50?L菽~?ッETS・;~Tセj?l・'・セリqP8臘 ユ~・nP>,「3ヲュセ雋ァ|エソユ・ 莅WヌPtNォ。JiN・・隆Ob yッ・?m! ウレR 箜鑈_P鵁t?cマV CEF=Vヨ)sAlィ"F?ャe。﨑オシキ・7Oン >$ ス?荿メtツク gヤモdt」Hォ2ヲ・K67!エルワ・跋lII?xO?゙x(<-`8$xE。裲ノ_イhチc"EZスqィ7Lチナ・=N_\khノ゚ゥ・ワgェu」ーVJ?#sレナ・NGz@・釚yヲ}"シAGラ5h韭iホjエャィ~?「~ソnslR%Q濬
全く読めないですね。
これで暗号化できていることが確認できました。
この暗号化ですが、
MySQL全体で1つのキーリングファイルを持っていて、
このキーリングファイルを使うことによって
復号できるようになっているようです。
キーリングファイルの場所は、
初期化パラメータ「keyring_file_data」で保持されています。
mysql> show global variables like 'keyring_file_data'; +-------------------+--------------------------------+ | Variable_name | Value | +-------------------+--------------------------------+ | keyring_file_data | /var/lib/mysql-keyring/keyring | +-------------------+--------------------------------+ 1 row in set (0.00 sec) mysql>
昨今、セキュリティというのはIT業界全体で重要性を増してきています。
MySQLは元々さほどセキュリティ等は厳しくない(=シンプルで使いやすい、ということにしておいてください笑)
製品でしたが、昨今の流れを汲んで、セキュリティ対策にも力を入れ始めているのでしょうか、、、
MySQL商用版では、
MySQL Enterprise Encryption, MySQL Enterprise Audit, MySQL Enterprise Firewallなど、
セキュリティ系の製品が次々とリリースされています。
これらの流れからみても、MySQLもセキュリティに力を入れ始めている(もしくは入れざるを得ない)
という事情があるのかな、と言えるのではないでしょうか。
今回はこんなところです。
では。