Express × TypeScriptでバックエンド開発②(MySQLの導入、ExpressでDB接続・操作)

## ご挨拶
<a href="https://qiita.com/oonon/items/e05d84ad64c9678e5ca2">Express × TypeScriptでバックエンド開発①(下準備~簡単なGET, POST)</a>
の続きです。
この記事では**ExpressでMySQLへ接続しGET・POST**します。
できる限りシンプルにハンズオンでまとめました。
皆様の新しいキャリア開拓の一助になればと思います。

### ▼ゴール
・ExpressでMySQLに接続する
・シンプルなAPIの実装（GET, POST）と動作確認

### ▼対象
・フロントエンドからキャリアを始めた人（ジュニア、ミドル）
・TypeScriptでバックエンド書いてみたい人

## MySQLをインストール
https://dev.mysql.com/downloads/windows/installer/8.0.html
にアクセスし、自分のOSを選択したうえでインストーラーをダウンロードしてください。
![mysqlinstaller.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/207237/2b644a7d-ee69-83a6-6dbe-8ac75bc63c59.png)

※ダウンロードにはOracleの会員登録・ログインが必要です。

インストーラーを起動、インストールを進めます。
※枚数多くてGIFにしました、見づらくてゴメンナサイ。
![MySQL_install.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/207237/3f02d870-cfb9-1584-9d2c-76c1fa21eab3.gif)

## MySQLのPATHを通す
MySQLにアクセスしてみます。
```
> mysql -uadmin -p
'mysql' は、内部コマンドまたは外部コマンド、
操作可能なプログラムまたはバッチ ファイルとして認識されていません。
```
パスを通す必要がありますね。
MySQLのbinフォルダのパスをコピーし、環境変数を編集・新規で登録（ペースト）します。
![MySQL_path.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/207237/1fd15414-b0a0-5b7b-c229-deac60cb063f.gif)


```
> mysql -uadmin -p
Enter password: ********
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 15
Server version: 8.0.30 MySQL Community Server - GPL

Copyright (c) 2000, 2022, Oracle and/or its affiliates.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.
```
パスが通りました。

## データベースを操作してみる
データベースを参照してみます。
```
mysql> SHOW databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| mysql              |
| performance_schema |
| sys                |
+--------------------+
4 rows in set (0.03 sec)
```
次にデータベースを作成し、切替を行います。
```
mysql> CREATE DATABASE sample_app;
Query OK, 1 row affected (0.01 sec)   <=== 作成できました

mysql> SHOW databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| mysql              |
| performance_schema |
| sample_app         |   <== 確認できました
| sys                |
+--------------------+
5 rows in set (0.00 sec)

mysql> USE sample_app;
Database changed   <== 切替できました
```
続いてテーブルを作成・確認します。
```
mysql> CREATE TABLE users (id INT AUTO_INCREMENT, email varchar(255) NOT NULL, password varchar(255), name varchar(255), PRIMARY KEY (id)) DEFAULT CHARSET=utf8;
Query OK, 0 rows affected, 1 warning (0.03 sec)

mysql> SHOW tables;
+----------------------+
| Tables_in_sample_app |
+----------------------+
| users                |
+----------------------+
1 row in set (0.00 sec)

mysql> DESCRIBE users;
+----------+--------------+------+-----+---------+----------------+
| Field    | Type         | Null | Key | Default | Extra          |
+----------+--------------+------+-----+---------+----------------+
| id       | int          | NO   | PRI | NULL    | auto_increment |
| email    | varchar(255) | NO   |     | NULL    |                |
| password | varchar(255) | YES  |     | NULL    |                |
| name     | varchar(255) | YES  |     | NULL    |                |
+----------+--------------+------+-----+---------+----------------+
4 rows in set (0.02 sec)

```

## ExpressからDB接続・操作する

コネクターとなるパッケージ"mysql2"をインストールします
```
npm install -D mysql2
```

srcフォルダ直下のindex.tsを以下の通り編集。
```typescript:index.ts
import express from 'express';
import usersController from './controllers/users';   <== 追記
import greetingController from './controllers/greetings';

const app: express.Express = express();

app.use(express.json());
app.use(express.urlencoded({ extended: true }));

app.use('/users', usersController);   <== 追記
app.use('/greetings', greetingController);

app.listen(5000, () => {
  console.log('Start on PORT:5000!');
});
```

controllerフォルダ直下にgreetings.tsを作成。
```typescript:users
import express, { Router, Request, Response } from 'express';
const mysql = require('mysql2');

const router: Router = express.Router();
type USER_TYPE = {
  id: null;
  email: string;
  password: string;
  name: string;
};

const connection = mysql.createConnection({
  host: 'localhost',
  user: 'admin',
  password: 'password',
  database: 'sample_app',
});

connection.connect((err: string) => {
  if (err) {
    console.log(err);
    return;
  }
  console.log('success');
});

router.get('/', (req: Request, res: Response) => {
  connection.query('SELECT * FROM `users`', (err: string, results: []) => {
    if (err) {
      console.log(err);
      return;
    }
    res.send(results);
  });
});

router.post('/', (req: Request, res: Response) => {
  connection.query(
    `insert into users values (0, "${req.body.email}", "${req.body.password}", "${req.body.name}")`,
    (err: string, results: []) => {
      if (err) {
        console.log(err);
        return;
      }
      res.send(results);
    }
  );
});

export default router;
```

**POSTする**
下記のように入力しSENDボタンを押下。
![user_post.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/207237/b97a5aff-42ac-b6b4-c292-41842b09cf30.png)

**GETする**
ブラウザで"localhost:5000/greetings"開く。
![user_get.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/207237/68e2f562-029a-9d9a-e8e6-10ef606dad20.png)
POSTしたユーザーoononを確認できました。

## おわりに
いかがだったでしょうか。
DB接続してデータ操作ができたと思います。
**認証・認可**は次回ご紹介します。