【第4回】bashを使って、S3にデータアップロード（自動化）

## 🎮 はじめに

これまで、スマブラ対戦データと天候データの収集を進めてきました。  
今回は、今までに収集したデータを**AWS S3にアップロードして管理する**ため、  
**bashスクリプトで自動化**していきます！

この記事では、

- Djangoから対戦結果データをCSV出力するPythonスクリプト
- bashを使ったS3アップロードスクリプト

の両方を紹介します！

---

## 🛠 使用技術

- Python（Djangoスクリプト）
- bash
- AWS CLI（S3アップロード）

---

## 🗃 やることまとめ

1. Djangoから試合データをCSVでエクスポート
2. bashスクリプトでS3にデータアップロード
---

### 1.Djangoから試合データをCSVでエクスポート

まず、Djangoのデータベースから対戦データを**CSVファイルとして出力**します。
実際のコードは以下になります。

このスクリプトは、manage.pyがあるフォルダに保存する想定で作成しています。
#### 📄 django_data_export.py

```python
import csv
import os
import django
import pytz

# Djangoの設定を読み込む
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "smash_bros_app_project.settings")
django.setup()

# Matchモデルをインポートする
from matches.models import Match

def export_to_csv(filename):
    # Matchの全データを取得
    data = Match.objects.all()
    # 日本時間のタイムゾーンオブジェクトを取得
    jst = pytz.timezone('Asia/Tokyo')
    
    # CSVファイルとして出力
    with open(filename, 'w', newline='', encoding='utf-8') as csvfile:
        fieldnames = [field.name for field in Match._meta.fields]
        writer = csv.DictWriter(csvfile, fieldnames=fieldnames)

        writer.writeheader()
        for obj in data:
            row = {}
            for field in fieldnames:
                value = getattr(obj, field)
                # 日時データがdatetimeオブジェクトであるかを確認
                if isinstance(value, django.utils.timezone.datetime):
                    # UTCから日本時間へ変換
                    value = value.astimezone(jst)
                    # 日時を指定のフォーマットに変換
                    value = value.strftime('%Y-%m-%d %H:%M:%S')
                row[field] = value
            writer.writerow(row)

if __name__ == "__main__":
    # 固定のファイルパスを指定
    file_path = 'S3_upload/django_data_export.csv'
    export_to_csv(file_path)
```
### 2.bashスクリプトでS3にデータアップロード
次に抽出したデータをS3にアップロードしていきます。
実際のコードは以下になります。

#### 📄 S3_upload.sh
```bash
#!/bin/bash

# Docker コンテナを開始
echo "Docker コンテナを起動中..."
docker start smash_app_export

# Docker コンテナ内で Python スクリプトをbash実行
# docker exec コマンドを使用して、コンテナ内でコマンドを実行します。
echo "Python スクリプトを実行中..."
docker exec -it smash_app_export sh \data_export.sh

#django_data_export.csv
docker cp 【Docker環境のcsvが保存されているパス】 【ローカル環境のcsvが保存されているパス】
#preterite_weather_export.csv
docker cp 【Docker環境のcsvが保存されているパス】 【ローカル環境のcsvが保存されているパス】

# スクリプトの実行が終了したら Docker コンテナを停止
echo "Docker コンテナを停止中..."
docker stop smash_app_export

#django_data_export.csv
aws s3 cp 【ローカル環境のcsvが保存されているパス】 【AWS S3のパス】

sleep 5

#preterite_weather_export.csv
aws s3 cp 【ローカル環境のcsvが保存されているパス】 【AWS S3のパス】

echo "処理が完了しました。"
```

#### 📄 data_export.sh
```bash
#!/bin/bash
# djangoエクスポートを実行
python django_data_export.py

# 気象データエクスポートを実行
python preterite_weather_export.py
```

全体の流れとしては、
**1. Dockerを起動**
**2. data_export.shを使って、前回の気象データ抽出スクリプトと今回のDjangoエクスポートスクリプトを実行**
**3. Dockerに保存したcsvを、ローカル環境にコピー**
**4. ローカル環境にコピーしたcsvを、S3にアップロード**

となります！

Dockerに保存したcsvをそのままアップロードせず、ローカル環境にコピーした理由としては、Docker環境にAWS認証の設定しようとすると、セキュリティのことを考慮しながら作成しないといけないので、そのリスクをなくすためローカルからアップロードする形で進めています。

また、「sleep 5」を書いた理由としては、
この後、AWS側で「preterite_weather_export.py」をS3にアップロードしたことをトリガーに、自動処理を進めるためになります。

以上がbashを使って、S3にデータアップロードするまでの流れになります。

---
## 🚀 次回

次回（第5回）は、AWS GlueとPySparkを使って、
対戦データと気象データを結合・加工するETL処理を構築していきます！

お楽しみに！
https://qiita.com/shota1212/items/47160952f26f69a1efcb

---