PHPサーバーと Amazon RDS DB インスタンスを作成する

## はじめに
[前回のあらすじ](https://qiita.com/udonnamerou/private/a5af859925ada849d082)
VPCで仮想ネットワーク環境を作成、ApacheウェブサーバーとRDS (MySQL)を作成する。
あと、[AWSのチュートリアル](https://docs.aws.amazon.com/ja_jp/AmazonRDS/latest/UserGuide/CHAP_Tutorials.WebServerDB.CreateWebServer.html)を見ながら進めていきます

## DBインスタンスを作成する
1. [Amazon RDS コンソール](https://console.aws.amazon.com/rds/)を開く
2. データベースの作成を選択
3. 設定を以下のように行う

- データベース作成方法を選択：Standard Createを選択
- エンジンオプション：MySQLを選択
- テンプレート：無料利用枠を選択
- DB インスタンス識別子：tutorial-db-instance
- マスターユーザー名：tutorial_user
- パスワードの自動生成:選択しない
- マスターパスワード：各自作成してね
- DBインスタンスサイズ：db.t2.micro
- ストレージ：すべてデフォルトの設定
- Virtual Private Cloud (VPC)：作成したVPCを使用
- 既存の VPC セキュリティグループ：プライベート用のVPCセキュリティグループを選択
- アベイラビリティーゾーン：指定なし
- データベースポート：3306
- 最初のデータベース名：sample

4.作成したRDSのエンドポイントとポート番号をメモ

## EC2インスタンスの作成とウェブサーバーのインストール
1. [Amazon EC2 コンソール](https://console.aws.amazon.com/ec2/)を開く
2.インスタンスの起動を選択
3. ステップ2：t2.microを選択
4. ステップ3：ネットワーク：作成したVPCを選択
5. ステップ3：サブネット：作成したパブリックサブネットを選択
6. ステップ3：自動割り当てパブリック IP：有効
7. ステップ4：ストレージの追加：何もしなくてよい
8. ステップ5：タグの追加：キー:Name, 値:tutorial-web-server
9. ステップ6：セキュリティグループ：tutorial-securitygroup
10. ステップ7：設定なし、起動ボタンをクリック
11. 既存のキーペア、もしくは新しいキーペアを作成する

## Apacheウェブサーバーのインストール
パブリックサブネットにウェブサーバーを立てたいのでEC2インスタンスに接続してみる。使用するソフトはTera Term

- ホスト名：先ほど作成したEC2インスタンスのパブリックIPv4 アドレス
- ユーザー名：ec2-user
- 秘密鍵：作成したキーペア（pemファイル）を使用

こういう画面が表示される
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/659464/efbf054c-a5c3-fa5e-9ec2-f2c4d261321c.png)

**updateの確認**
yumとはパッケージ管理システムのコマンド
-y とは問い合わせ全てにYesと答える

```
$ sudo yum update -y
```

 PHP ソフトウェアパッケージを使用して、Apache ウェブサーバーをインストール

```
$ sudo yum install -y httpd php php-mysqlnd
```

ウェブサーバーを起動

```
$ sudo service httpd start
```

Apacheがインストールできたので、Apacheを入れたEC2インスタンスのパブリックIPv4DNSをブラウザのアドレスバーに入力すると、Apacheテストページが表示されるようになるはず。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/659464/d5d43e0a-42ef-4c22-e182-863d2c6b9aff.png)

## Apacheウェブサーバーの設定
chkconfig コマンドを使用して、システムがブートするたびにウェブサーバーが起動するように設定

```
sudo chkconfig httpd on
```

**Apache ウェブサーバーのファイルアクセス許可を設定**
ec2-user が Apache ウェブサーバーのデフォルトルートディレクトリにあるファイルを管理するために、/var/www ディレクトリの所有権とアクセス許可を変更する。


```
$ sudo groupadd www  
```

ec2-user ユーザーを www グループに追加。

```
$ sudo usermod -a -G www ec2-user
```

一度ログアウトする

```
$ exit 
```
再度ログイン、groups コマンドを使用して www グループが存在していることを確認

```
$ groups
ec2-user adm wheel systemd-journal www
```
/var/www およびそのサブディレクトリのディレクトリアクセス許可を変更して、グループの書き込みアクセス許可を追加し、後で作成するサブディレクトリのグループ ID を設定していく。

#### コマンドの補足
chmodはファイルに権限を設定するコマンド
2775って何？と思うが、これは[ファイルパーミッション](https://blog.fenrir-inc.com/jp/2012/02/file_permission.html)というものらしい。

またfind folderName -type d でサブディレクトリを検索し、 -execで検索結果に対してコマンドを実行するようにしている。

```
[ec2-user ~]$ sudo chmod 2775 /var/www
[ec2-user ~]$ find /var/www -type d -exec sudo chmod 2775 {} +
```                
先ほどと同じように、ファイルごとにアクセス許可を繰り返し変更し、グループの書き込みアクセス許可を追加していく。

```
[ec2-user ~]$ find /var/www -type f -exec sudo chmod 0664 {} +                
```
※ 動作確認のため、パーミッションを緩く設定しています。本来であれば専用のユーザーを作成すべきところですが割愛しています。

## ApacheウェブサーバをDBインスタンスに接続する

以下のコマンドを実行

```
[ec2-user ~]$ cd /var/www
[ec2-user ~]$ mkdir inc
[ec2-user ~]$ cd inc
```

inc という dbinfo.inc ディレクトリに新しいファイルを作成し、ファイルを編集

```
[ec2-user ~]$ nano dbinfo.inc
```

dbinfoにはDBインスタンス接続に必要な情報をまとめたファイルを書いていく。書いたら保存。

```
<?php

define('DB_SERVER', 'db_instance_endpoint');
define('DB_USERNAME', 'tutorial_user');
define('DB_PASSWORD', 'master password');
define('DB_DATABASE', 'sample');

?>
```

※あくまでテスト用なので、dbinfoにパスワードをべた書きしています。本来は権限を絞ったユーザーを別に作成したうえで、環境変数などから読み込みべきですが割愛しています。

ディレクトリを /var/www/html に変更
この/var/www/htmlは[ドキュメントルート](http://ftp.lumica.co.jp/_webserver/document_root.html)といって、HTMLファイルの置き場として使える。

```
[ec2-user ~]$ cd /var/www/html
```

SamplePage.phpを作成

```
nano SamplePage.php
```

次のコードを追加していく

```
<?php include "../inc/dbinfo.inc"; ?>
<html>
<body>
<h1>Sample page</h1>
<?php

  /* Connect to MySQL and select the database. */
  $connection = mysqli_connect(DB_SERVER, DB_USERNAME, DB_PASSWORD);

  if (mysqli_connect_errno()) echo "Failed to connect to MySQL: " . mysqli_connect_error();

  $database = mysqli_select_db($connection, DB_DATABASE);

  /* Ensure that the EMPLOYEES table exists. */
  VerifyEmployeesTable($connection, DB_DATABASE);

  /* If input fields are populated, add a row to the EMPLOYEES table. */
  $employee_name = htmlentities($_POST['NAME']);
  $employee_address = htmlentities($_POST['ADDRESS']);

  if (strlen($employee_name) || strlen($employee_address)) {
    AddEmployee($connection, $employee_name, $employee_address);
  }
?>

<!-- Input form -->
<form action="<?PHP echo $_SERVER['SCRIPT_NAME'] ?>" method="POST">
  <table border="0">
    <tr>
      <td>NAME</td>
      <td>ADDRESS</td>
    </tr>
    <tr>
      <td>
        <input type="text" name="NAME" maxlength="45" size="30" />
      </td>
      <td>
        <input type="text" name="ADDRESS" maxlength="90" size="60" />
      </td>
      <td>
        <input type="submit" value="Add Data" />
      </td>
    </tr>
  </table>
</form>

<!-- Display table data. -->
<table border="1" cellpadding="2" cellspacing="2">
  <tr>
    <td>ID</td>
    <td>NAME</td>
    <td>ADDRESS</td>
  </tr>

<?php

$result = mysqli_query($connection, "SELECT * FROM EMPLOYEES");

while($query_data = mysqli_fetch_row($result)) {
  echo "<tr>";
  echo "<td>",$query_data[0], "</td>",
       "<td>",$query_data[1], "</td>",
       "<td>",$query_data[2], "</td>";
  echo "</tr>";
}
?>

</table>

<!-- Clean up. -->
<?php

  mysqli_free_result($result);
  mysqli_close($connection);

?>

</body>
</html>


<?php

/* Add an employee to the table. */
function AddEmployee($connection, $name, $address) {
   $n = mysqli_real_escape_string($connection, $name);
   $a = mysqli_real_escape_string($connection, $address);

   $query = "INSERT INTO EMPLOYEES (NAME, ADDRESS) VALUES ('$n', '$a');";

   if(!mysqli_query($connection, $query)) echo("<p>Error adding employee data.</p>");
}

/* Check whether the table exists and, if not, create it. */
function VerifyEmployeesTable($connection, $dbName) {
  if(!TableExists("EMPLOYEES", $connection, $dbName))
  {
     $query = "CREATE TABLE EMPLOYEES (
         ID int(11) UNSIGNED AUTO_INCREMENT PRIMARY KEY,
         NAME VARCHAR(45),
         ADDRESS VARCHAR(90)
       )";

     if(!mysqli_query($connection, $query)) echo("<p>Error creating table.</p>");
  }
}

/* Check for the existence of a table. */
function TableExists($tableName, $connection, $dbName) {
  $t = mysqli_real_escape_string($connection, $tableName);
  $d = mysqli_real_escape_string($connection, $dbName);

  $checktable = mysqli_query($connection,
      "SELECT TABLE_NAME FROM information_schema.TABLES WHERE TABLE_NAME = '$t' AND TABLE_SCHEMA = '$d'");

  if(mysqli_num_rows($checktable) > 0) return true;

  return false;
}
?>             
```

ウェブプラウザから ```http://EC2 instance endpoint/SamplePage.php```を開けばDBインスタンスが接続できていることを確認できる。