UNIX/Linuxの部屋 コマンド:mysql MySQL データベースにアクセスするためのコマンド


※空白区切りで AND 検索 (例:「ファイル 削除」)

コマンド mysql MySQL データベースにアクセスするためのコマンド

mysql コマンドは、MySQL データベースにアクセスするためのコマンドである。つまり MySQL のクライアントアプリケーションである。mysql コマンドを使って、テーブルの管理や SELECT・INSERT などの SQL 文を実行することができる。

接続
mysql コマンドは、引数なしの場合、
  • 接続先は同じサーバ内の UNIX ドメインソケット (/var/lib/mysql/mysql.sock や /tmp/mysql.sock など)
  • ユーザ名は自分の UNIX ユーザ名
  • パスワードは空
に接続しようとする。

下記のオプションを駆使して頑張って接続してほしい。

-u [ユーザ名] または --user=[ユーザ名]
-h [ホスト名] または --host=[ホスト名]
-p または --password=[パスワード]
-P または --port=[ポート番号]
-d [データベース名] または --database=[データベース名] または [データベース名]

最終的には
mysql>
というプロンプトが出れば OK である。

データベース操作
接続後、デフォルトとするデータベースを選択する。
USE [データベース名]
USE を書けば便利というだけで、書かなくてはならないものではない。一度 USE すれば
SELECT * FROM [データベース名].[テーブル名];

SELECT * FROM [テーブル名];
と短く書ける、というだけの話である。
データベースの一覧を表示
SHOW DATABASES;
データベースを新規作成
CREATE DATABASE [データベース名];
既存データベースの CREATE DATABASE 文を出力する
SHOW CREATE DATABASE [データベース名];

テーブル操作
テーブルの一覧を表示
SHOW TABLES;
→ 現在 USE で選択中のデータベースに含まれるテーブル一覧を表示する。
SHOW TABLES LIKE '%abc%';
→ テーブル名に abc を含むテーブル一覧を表示する。
SHOW TABLES FROM [データベース名];
→ 現在 USE で選択中でない場合でも、FROM [データベース名] で指定可能。
テーブルの詳細情報を表示
SHOW TABLE STATUS
テーブルの作成
CREATE TABLE [テーブル名] (カラム定義) Engine=InnoDB;
→ Engine がよくわからなければ、InnoDB で作っておくこと。
テーブルのコピー
CREATE TABLE [新テーブル名] AS SELECT * FROM [旧テーブル];
→ 旧テーブルと同じテーブルを作成し、データもコピーする。
テーブルのコピー (データなし)
CREATE TABLE [新テーブル名] AS SELECT * FROM [旧テーブル] WHERE 1=0;
→ 旧テーブルと同じテーブルを作成するが、データはコピーしない。
テーブルの削除
DROP TABLE [テーブル名];
テーブルの CREATE 文を表示する
SHOW CREATE TABLE [テーブル名];
テーブル名の変更
ALTER TABLE [旧テーブル名] RENAME TO [新テーブル名]

カラム追加・削除・表示
テーブルのカラム情報を表示
SHOW COLUMNS FROM [テーブル名];
mysql> SHOW COLUMNS FROM mytable;
+-----------------+------------+------+-----+---------+-------+
| Field           | Type       | Null | Key | Default | Extra |
+-----------------+------------+------+-----+---------+-------+
| foo_id          | int(11)    | NO   | PRI | NULL    |       |
| mytext          | mediumtext | NO   |     | NULL    |       |
| display_order   | int(11)    | NO   |     | NULL    |       |
| enable_flag     | tinyint(1) | NO   |     | NULL    |       |
| insert_datetime | datetime   | NO   |     | NULL    |       |
| update_datetime | datetime   | NO   |     | NULL    |       |
+-----------------+------------+------+-----+---------+-------+
6 rows in set (0.00 sec)
なお、DESC、DESCRIPTION、SHOW FIELDS でも同じ。
SHOW FULL COLUMNS FROM [テーブル名];
SHOW COLUMNS に Collation・Privileges を追加したより詳細な情報を表示。
カラムの追加
ALTER TABLE [テーブル名] ADD COLUMN [カラム定義]
→ カラムがテーブルの末尾に追加される
ALTER TABLE [テーブル名] ADD COLUMN ([カラム定義1], [カラム定義2], ...)
→ 複数カラムを同時に追加
ALTER TABLE [テーブル名] ADD COLUMN [カラム定義] FIRST
→ テーブルの先頭に移動
ALTER TABLE [テーブル名] ADD COLUMN [カラム定義] AFTER [既存カラム名]
→ [既存カラム] の後に追加
カラム名の変更 + カラム型・定義の変更
ALTER TABLE [テーブル名] CHANGE [旧カラム名] [新カラム名] [新カラム定義]
カラム名だけを変更したい (カラム定義は変えたくない) 場合であっても、DEFAULT や NOT NULL などのカラム定義は必ず指定しないといけない。現在のカラム定義と異なるものを指定してしまうと
カラム型・定義の変更
ALTER TABLE [テーブル名] MODIFY [カラム名] [新カラム定義]
DEFAULT 句のみの変更
ALTER TABLE [テーブル名] ALTER [カラム名] SET DEFAULT [デフォルト値]
ALTER TABLE [テーブル名] ALTER [カラム名] DROP DEFAULT
→ データ出力が不要なので、MODIFY より速い。
インデックス
インデックスの作成
ALTER TABLE [テーブル名] ADD INDEX [インデックス名] (col1)
ALTER TABLE [テーブル名] ADD INDEX index_name (col1, col2)
→ 複合インデックスの場合
インデックスの削除
ALTER TABLE [テーブル名] DROP INDEX index_name;
ALTER TABLE [テーブル名] ADD UNIQUE (col1);
ALTER TABLE [テーブル名] ADD PRIMARY KEY (col1);
ALTER TABLE [テーブル名] DROP PRIMARY KEY;
インデックスの確認
SHOW INDEX FROM [テーブル名];
または
SELECT table_schema, table_name, index_name, column_name, seq_in_index
FROM information_schema.statistics
WHERE table_schema = 'mydb' AND table_name = 'mytable'
システム変数など
システム変数を表示する。
SHOW VARIABLES;
→ 全変数を表示。
SHOW VARIABLES like '%abc%';
→ 変数名で絞ることもできる。
(★GLOBAL と SESSION について要追記)

SHOW STATUS

プロセス
プロセスの一覧を確認
SHOW PROCESSLIST
SQL 省略なしでプロセスの一覧を確認 (長くなるので \G をおすすめする)
SHOW FULL PROCESSLIST
重い SQL を確認したら、KILL コマンドでプロセスを殺す。

型 (整数型)
整数型 TINYINT 1バイト -128〜127
整数型 TINYINT UNSIGNED 1バイト 0〜255
整数型 SMALLINT 2バイト -32768〜32767
整数型 SMALLINT UNSIGNED 2バイト 0〜65535
整数型 MEDIUMINT 3バイト -8388608〜8388607
整数型 INT 4バイト -2147483648〜2147483647
整数型 BIGINT 8バイト -9223372036854775808〜9223372036854775807

TINYINT(1) や INT(2) といった書き方ができるが、これは領域長を示すものではなく、単なる表示幅である。TINYINT はあくまで 1バイトであるし、INT はあくまで 4バイトである。

表示幅とは何かと言うと、ゼロパディングをする ZEROFILL を設定したとき、この表示幅が使われる。実体としては単なる TINYINT なので、あくまで表示の際にゼロパディングしているだけである。
mysql> CREATE TABLE mytable (
  col1 TINYINT(2) ZEROFILL,
  col2 TINYINT(10) ZEROFILL
);
mysql> insert into mytable values (1,2);
Query OK, 1 row affected (0.01 sec)

mysql> select * from mytable;
+------+------------+
| col1 | col2       |
+------+------------+
|   01 | 0000000002 |
+------+------------+
ただ、SELECT col1+1, col2+1 としただけでゼロパディングがなされないような中途半端なものを本当に使うべきなのかよく考えた方がよいと思う。

型 (固定小数型)
DECIMAL(N,M)
小数部 M 桁を含む、全体で N 桁の数を保持できる。DECIMAL(5,2) であれば、-999.99〜999.99 となる。
DECIMAL(N)
桁数 N 桁の整数を保持できる。DECIMAL(3) であれば、-999〜999 となる。DECIMAL(N) は DECIMAL(N,0) と同じ。
DECIMAL(N,M) UNSIGNED
マイナスが使えなくなる以外は DECIMAL(N,M) と同じ。

N の最大は 65 である。よって、DECIMAL(65)、DECIMAL(65,5)、DECIMAL(65,45) などが可能である(それぞれ、整数部65桁・小数部なし、整数部60桁・小数部5桁、整数部20桁・小数部45桁)。

MySQL では NUMERIC は DECIMAL の別名である。

型 (日付)
DATE
年月日を保持する。範囲は '1000-01-01' から '9999-12-31'。
データサイズは、3バイト。
DATETIME
年月日時分秒を保持する。範囲は '1000-01-01 00:00:00' から '9999-12-31 23:59:59'。ミリ秒・マイクロ秒は扱えない。
データサイズは、MySQL 5.6.3 までは 8バイト。MySQL 5.6.4 以降は 5バイト + 小数秒サイズ。
TIMESTAMP
年月日時分秒に加え、マイクロ秒まで保持する。範囲は '1970-01-01 00:00:01' から '2038-01-19 03:14:07'。
MySQL 5.6.3 までは、DEFAULT current_timestamp を指定できるのは TIMESTAMP だけであったが、MySQL 5.6.4 以降は TIMESTAMP も DATETIME も指定できるようになった。
データサイズは、MySQL 5.6.3 までは 4バイト。MySQL 5.6.4 以降は 4バイト + 小数秒サイズ。

上記の、小数秒サイズとは何かと言うと、下記のように必要な精度によって変わる。
小数秒精度 必要なサイズ
0 0バイト
1〜2桁 1バイト
3〜4桁 2バイト
5〜6桁 3 バイト

要はこういうことだ。
MySQL 5.6.3以前 + DATETIME 8バイト
MySQL 5.6.4以降 + DATETIME(0) 5バイト
MySQL 5.6.4以降 + DATETIME(1) または DATETIME(2) 6バイト
MySQL 5.6.4以降 + DATETIME(3) または DATETIME(4) 7バイト
MySQL 5.6.4以降 + DATETIME(5) または DATETIME(6) 8バイト

他にも YEAR 型・TIME 型がある。

型 (文字列型)
CHAR
長さは 0〜255。例えば CHAR(5) とした上で 'abcd' という値を入れると、SELECT 時には 'abcd ' と末尾に空白が付いた形で受け取ることになる。
VARCAHR(N)
N は文字数。最大領域は 65535バイトだが、UTF-8 だと 1文字3バイトだったり、最近は 1文字4バイト(?)だったり、管理用の領域があったりして、UTF-8 の場合は最大 VARCHAR(21844) らしい。
型 (BLOB)
TINYBLOB
BLOB
MEDIUMBLOB
LONGBLOB

型 (TEXT)
TINYTEXT
TEXT
MEDIUMTEXT
LONGTEXT

SELECT
SELECT * FROM TABLE;
SELECT 'abc', 123, now()
→ MySQL は FROM なしでも可能。Oracle は必須なので FROM dual とする。

ORDER BY
SELECT * FROM TABLE ORDER BY col1;
→ col1 の昇順でソートする。
SELECT * FROM TABLE ORDER BY col1 ASC;
→ ASC を明示的につけても同じ挙動 (ASC=ascending)。
SELECT * FROM TABLE ORDER BY col1 DESC;
→ DESC とすると降順 (DESC=Descending)。
SELECT * FROM TABLE ORDER BY col1, col2;
→ col1 の昇順でソートし、col1 が同じ値の場合は col2 の昇順でソートする。
SELECT * FROM TABLE ORDER BY col1 DESC, col2 ASC;
→ col1 は降順、col2 は昇順とすることもできる。
SELECT * FROM TABLE ORDER BY (CASE WHEN col1=9999 then 0 else col1 END)
→ CASE 文でより複雑な書き方もできる。この例では col1 の 9999 は特殊値なので 0 と同じに扱っている)
SELECT * FROM TABLE ORDER BY (CASE WHEN col1=9999 then 0 else col1 END) DESC, col2 ASC
→ CASE 文と、カラムをつなげることもできる。
昇順・降順とは、についてはいつか書く (照合順序・Collation)。

WHERE
SELECT * FROM TABLE WHERE col1 = 'X';
SELECT * FROM TABLE WHERE col1 = 'X' AND col2 = 'Y';
SELECT * FROM TABLE WHERE val1 < 100 OR val2 > 200;
SELECT * FROM TABLE WHERE val1 <= 100 OR val2 >= 200;
SELECT * FROM TABLE WHERE val1 LIKE '%abc';
→ abc で終わる
SELECT * FROM TABLE WHERE val1 LIKE '%abc%';
→ abc が含まれる
SELECT * FROM TABLE WHERE val1 LIKE 'abc%';
→ abc で始まる
SELECT * FROM TABLE WHERE val1 LIKE 'a_';
→ a のあとに任意の 1文字が続く
SELECT * FROM TABLE WHERE val1 BETWEEN 100 AND 200;
→ 100 <= val1 AND val1 <= 200 と同じ
SELECT * FROM TABLE WHERE val1 IN (1,2,3,4);
SELECT * FROM TABLE WHERE val1 IN (SELECT xxx FROM yyy)
SELECT * FROM TABLE WHERE val1 NOT IN (SELECT xxx FROM yyy)

GROUP BY
SELECT col1, COUNT(*) FROM TABLE GROUP BY col1;
SELECT col1, MAX(col2) FROM TABLE GROUP BY col1;
SELECT col1, COUNT(*) FROM TABLE GROUP BY col1 HAVING COUNT(*)>4;

DISTINCT
SELECT DISTINCT col1 FROM TABLE;
→ col1 の重複を取り除いて取得
SELECT DISTINCT col2, col3 FROM TABLE;
→ 複数カラムに対して distinct
SELECT COUNT(DISTINCT col1) FROM TABLE;
→ col1 の種類数を数える (重複除外した上でのカウント)

SELECT の LIMIT
SELECT * FROM mytable LIMIT 10;
→ 先頭10行のみ出力
SELECT * FROM mytable LIMIT 5, 10;
→ 先頭6行目 (0行目からカウント) を先頭に 10行分を出力 (つまり 6〜15行目)

SELECT の、おおむね全部のせ
SQL の書き方には順序が決められている。以下、SELECT の主要な構文を載せてみたので参考にしてほしい。
SELECT DISTINCT col1
FROM mytable
WHERE col2=1
GROUP BY col3, col4
HAVING count(*)>1
ORDER BY col5 asc, col6 desc
LIMIT 10, 5;
ちなみに、評価順は下記となる。
1. FROM mytable (mytable から)
2. WHERE col2=1 (col2=1 なレコードを抽出し)
3. GROUP BY col3, col4 (col3 と col4 で集約し)
4. HAVING count(*)>1 (col3 と col4 で集約した結果、2行以上あるものを選び)
5. SELECT MAX(col1) (co3 と col4 で集約した結果それぞれで最大の col1 を選び)
6. ORDER BY col3 ASC, col4 DESC (col3 の昇順、col3 が同じなら col4 の降順でソートし)
7. LIMIT 10, 5 (9行目から 5行を出力する)

文字列関数
文字列結合 (CONCAT)
SELECT CONCAT(123, ' a ',NOW());
→ || で文字列結合したいなら PIPES_AS_CONCAT 変数の設定が必要

NULL
SELECT * FROM mytable WHERE col IS NULL;
→ NULL 確認は = NULL ではなく IS NULL で。
SELECT * FROM mytable WHERE col IS NOT NULL;
→ NULL じゃない場合は、IS NOT NULL。
SELECT IFNULL(col, 'NULLでした') FROM mytable;
→ col が NULL なら、"NULLでした" に置換。NULL でないならそのまま。
SELECT * FROM mytable WHERE IFNULL(col, 0) <10;
→ col が NULL なら 0 に置換した上で、10 と比較。IFNULL なしだと unknown になり、ヒットしない。

正規表現
SELECT * FROM TABLE WHERE val1 REGEXP 'abc';
→ abc が含まれる
SELECT * FROM TABLE WHERE val1 REGEXP '.*abc';
→ abc で終わる
SELECT * FROM TABLE WHERE val1 REGEXP 'abc.*';
→ abc で始まる
SELECT * FROM TABLE WHERE val1 REGEXP '^[0-9][0-9][0-9][0-9]/[0-9][0-9]?/[0-9][0-9]?$';
→ 2017/04/01 でも 2017/4/1 でもひっかかるように

コメント
MySQL では「#」「--」「/* 〜 */」の 3種類のコメントを受け付ける。「--」の後には半角スペース・タブ・改行が必要であることに注意。
SELECT 1; # ここはコメント
SELECT 1; -- ここはコメント
SELECT 1; /* ここはコメント */
SELECT 1; /* 複数行の
コメント */
ただし「/*! 〜 */」は MySQL には解釈される。
SELECT /*! STRAIGHT_JOIN */ col1 FROM table1,table2 WHERE ...
は MySQL にとっては
SELECT STRAIGHT_JOIN col1 FROM table1,table2 WHERE ...
と同じ。

ヒント句


INSERT
テーブルに 1行追加する。
INSERT INTO [テーブル名] VALUES (1, 'A', NOW());
省略せずに書くならば、下記のようにカラム名を列挙する。
INSERT INTO [テーブル名] (カラム1, カラム2, カラム3) VALUES (1, 'A', NOW());
SHOW COLUMNS の並び順通りに書く場合、カラム名の列挙は省略できる。

テーブルに複数行を追加する。
INSERT INTO [テーブル名] VALUES
(2, 'C', NOW()),
(3, 'E', NOW()),
(4, 'G', NOW());
INSERT 時にプライマリキーの重複が発生した場合、UPDATE で更新する。
INSERT INTO [テーブル名] (col1, col2) VALUES (1, 'a')
ON DUPLICATE KEY UPDATE col2='a';
→ col1 が主キーでそれがかぶった場合、UPDATE col2='a' WHERE col1=1 的な処理を行う。
複数行 INSERT でキー重複した場合、"VALUES (カラム名)" という書き方が便利。
INSERT INTO [テーブル名] (col1, col2) VALUES (1, 'a'), (2, 'b')
ON DUPLICATE KEY UPDATE col2= VALUES (col2);
→ 行に応じて UPDATE SET col2='a' になったり、UPDATE SET col2='b' になったりする。
★update set col=default、update set col2=default(col1) という書き方もある。

DELETE
全レコード削除
DELETE FROM [テーブル名];
→ 全レコード削除。TRUNCATE の使用も検討すること。ロールバック可能。
特定レコード削除
DELETE FROM [テーブル名] WHERE col1 = 1;
最大N行削除
DELETE FROM [テーブル名] LIMIT 100;
→ DELETE の LIMIT には最大件数しか書けない

UPDATE
全行更新
UPDATE [テーブル名] SET col1 = 1;
UPDATE [テーブル名] SET col1 = NULL;
条件指定
UPDATE [テーブル名] SET col1 = 1 WHERE col2 > 100
最大N行更新
UPDATE [テーブル名] SET col1 = 1 WHERE col1 IS NULL LIMIT 100;
→ UPDATE の LIMIT には最大件数しか書けない
別テーブルから値を転記
UPDATE items, month SET items.price = month.price
WHERE items.id = month.id;
上記の書き方は、MySQL では 「複数テーブル構文」と呼ぶらしい。ちなみに Oracle では下記のようにするが、A は MySQL でも成功、B は失敗した。
-- A: 1カラム更新
UPDATE items SET price = (SELECT price FROM month WHERE id=items.id);
-- B: 複数カラム更新
UPDATE items SET (price_tax, price_notax) = (SELECT price_tax, price_notax FROM month WHERE id=items.id);

TRUNCATE
TRUNCATE TABLE [テーブル名]
全レコード削除。ロールバック不可。ちなみに PostgreSQL では TRUNCATE もロールバックできたりする。

explain
quit
終了

Tips1. mysql コマンドプロンプトでの入力のクリア
mysql> seleeeect col1
->
→ select のつづりを間違えたことに気づいたが、すでに Enter を押してしまっている。
こういうとき Ctrl-c で mysql コマンド自体を終わらせたり、セミコロンで無理やりエラーにしてしまったり、としている人もいるかと思うのだが、\c で入力バッファのクリアができる。
mysql> seleeeect col1
-> \c
→ 入力途中のものはなかったことになる
mysql> seleeeect col1
-> aaaa\c
→ 途中まで入力した後に \c でもよい。
実は mysql コマンド起動直後にもそう書いてある。
Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.
ただし、
mysql> seleeeect "aaa
"> \c
→ "" 内部なのでクリアできない
などとクォート内部だったりするとクリアできない ("" を閉じてから \c しないといけない)。

MySQL 5.7.1 以降なら、Ctrl-c でもバッファクリアできる (それ以前のバージョンでは mysql コマンドが終了してしまう)。

Tips2. \G
SELECT 文などの行末を ; ではなく \G で終わらせると、表形式ではなく、縦に並べてくれる。

通常の SELECT:
mysql> select * from t;
+------+------+
| a0   | a1   |
+------+------+
|    0 |    0 |
|  100 |  200 |
+------+------+
2 rows in set (0.00 sec)
\G な SELECT:
mysql> select * from t\G
*************************** 1. row ***************************
a0: 0
a1: 0
*************************** 2. row ***************************
a0: 100
a1: 200
2 rows in set (0.05 sec)

通常の SHOW TABLES
mysql> show tables;
+------------------+
| Tables_in_mytest |
+-----------------+|
| table1           |
| table2           |
| table3           |
+------------------+
3 rows in set (0.02 sec)
\G な SHOW TABLES
mysql> show tables\G
*************************** 1. row ***************************
Tables_in_mytest: t
*************************** 2. row ***************************
Tables_in_mytest: t2
*************************** 3. row ***************************
Tables_in_mytest: t3
3 rows in set (0.00 sec)

通常の SHOW COLUMNS (DESC)
mysql> desc t;
+-------+------------+------+-----+---------+-------+
| Field | Type       | Null | Key | Default | Extra |
+-------+------------+------+-----+---------+-------+
| a0    | tinyint(4) | YES  |     | NULL    |       |
| a1    | tinyint(1) | YES  |     | NULL    |       |
+-------+------------+------+-----+---------+-------+
2 rows in set (0.27 sec)
\G な SHOW COLUMNS (DESC)
mysql> desc t\G
*************************** 1. row ***************************
  Field: a0
   Type: tinyint(4)
   Null: YES
    Key:
Default: NULL
  Extra:
*************************** 2. row ***************************
  Field: a1
   Type: tinyint(1)
   Null: YES
    Key:
Default: NULL
  Extra:



頑張って書いたおすすめコンテンツ!