Chart.jsを利用してグラフを表示する

前回の記事でAzure SQL Databaseに値を保存し、Web Appsから表示することができたので、この値を利用してグラフ描写してみたいと思います。

[Azure Web AppsからAzure SQL Databaseに接続して値を表示したい #Azure - Qiita](https://qiita.com/teraco/items/87b70c8d9873d60e06d5#%E3%82%B9%E3%83%86%E3%83%83%E3%83%972-3-azure-web-app%E3%81%8B%E3%82%89%E6%8E%A5%E7%B6%9A%E6%96%87%E5%AD%97%E5%88%97%E3%82%92%E8%AA%AD%E3%81%BF%E5%8F%96%E3%81%A3%E3%81%A6%E3%82%A2%E3%82%AF%E3%82%BB%E3%82%B9)

### 完成したもの

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/147841/90551445-7d00-3946-08b4-68991b27c33f.png)

### 構成

```
project-root/
│
├── public/
│   └── index.html
├── node_modules/
├── .env
├── package.json
├── package-lock.json
└── index.js
```

### コード

```public/index.html
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Chart.js Example</title>
    <script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
</head>
<body>
    <div style="width: 50%; margin: auto;">
        <canvas id="myChart"></canvas>
    </div>
    <script>
        async function fetchData() {
            // データ取得
            const response = await fetch('/data');
            const data = await response.json();

            // グラフを描画
            const ctx = document.getElementById('myChart').getContext('2d');
            new Chart(ctx, {
                type: 'line', // グラフの種類（折れ線グラフ）
                data: {
                    labels: data.map((_, index) => `Point ${index + 1}`), // ラベル
                    datasets: [{
                        label: 'Sample Data',
                        data: data, // 値
                        borderColor: 'blue',
                        borderWidth: 2,
                        fill: false
                    }]
                },
                options: {
                    responsive: true,
                    scales: {
                        y: {
                            beginAtZero: true
                        }
                    }
                }
            });
        }

        // データ取得とグラフ描画の実行
        fetchData();
    </script>
</body>
</html>

```

```index.js
require('dotenv').config();

console.log("DB_SERVER:", process.env.DB_SERVER);

const express = require('express');
const sql = require('mssql');
const app = express();

// SQL Server接続設定
const config = {
    user: process.env.DB_USER,
    password: process.env.DB_PASSWORD,
    server: process.env.DB_SERVER,
    database: process.env.DB_NAME,
    options: {
        encrypt: true, // Azureでは必須
        trustServerCertificate: false
    },
    requestTimeout: 30000
};

// データ取得用エンドポイント
app.get('/data', async (req, res) => {
    try {
        // データベース接続
        const pool = await sql.connect(config);
        const result = await pool.request().query('SELECT Value FROM DataPoints');
        
        // 結果をJSONで返す
        res.json(result.recordset.map(row => row.Value));
    } catch (err) {
        console.error('エラー:', err.message);
        res.status(500).send('エラーが発生しました');
    }
});

// 静的ファイルを提供
app.use(express.static('public'));

// サーバーを起動
const PORT = process.env.PORT || 3000;
app.listen(PORT, () => {
    console.log(`Server running on port ${PORT}`);
});

```

### 解説

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/147841/b3c16aed-4f74-046a-b441-533b0d0e6151.png)

- index.jsがDBへのアクセスを担うバックエンド的存在
- publick/index.htmlがフロントエンド的存在

1. ブラウザがindex.htmlなど要求
1. index.jsが応答し、app.use(express.static('public'));を実行
1. 指定されたpublic/index.html を読み込み
1. public/index.html 内の const response = await fetch('/data'); により、index.js内の/data配下を呼び出し
1. /data配下のSQL文でDBにアクセス
1. DBから帰ってきた値をindex.jsが読み込み
1. 最終的にグラフ描写