## 前言
這邊文章紀錄使用 .net core 7 MVC 連線到mysql資料庫,進行基本CRUD的操作
以下是完成後的結果

接下來將以資料庫建立、 註冊服務 、 DbContext 、appsettings.json、API Controller 的實作進行說明
## 資料庫建立
先透過mysqlworkbench在本地端建立
``` sql=
create database TestConn;
use TestConn;
create table Connection(ConnectionId INT AUTO_INCREMENT PRIMARY KEY, ConnStr varchar(100), Remark varchar(100));
insert Connection(Connstr, remark) values('conn1', 'remark1');
insert Connection(Connstr, remark) values('conn2', 'remark2');
insert Connection(Connstr, remark) values('conn3', 'remark3');
```

## DbContext & Model
建立Connection類別
```csharp=
public class Connection
{
[Key]
public int ConnectionId { get; set; }
public string ConnStr { get; set; }
public string Remark { get; set; }
}
```
建立 DbContext
```csharp=
public class TestConnDBContext : DbContext
{
public DbSet<Connection> Connection { get; set; }
public TestConnDBContext(DbContextOptions<TestConnDBContext> options) : base(options)
{
}
}
```
### DbContext介紹
`DbContext` 是 Entity Framework (EF) 中的一個基本類別,它代表了與資料庫的一次會話,並允許您對資料庫進行 CRUD(創建、讀取、更新、刪除)操作。在使用 Entity Framework 進行 .NET 應用程序開發時,您會操作 DbContext 類別的實例來與資料庫互動。
以下是 `DbContext` 的一些主要功能:
1. **查詢:**
使用 LINQ(Language Integrated Query)語言,可以寫出類似於 SQL 的查詢來從資料庫檢索資料。Entity Framework 會將這些 LINQ 查詢轉換成適合資料庫的 SQL 查詢。
2. **保存變更:**
在內存中對實體進行增刪改操作後,可以通過 `DbContext` 提供的 `SaveChanges()` 方法把這些變更保存到資料庫中。這個過程包括生成對應的 SQL 命令並執行它們。
3. **跟蹤變更:**
`DbContext` 會自動跟蹤實體的變更狀態,當您對實體進行操作時,它會知道實體是被新增、修改還是刪除了。當調用 `SaveChanges()` 方法時,`DbContext` 會根據實體的狀態生成相應的 SQL 語句。
4. **緩存:**
第一次查詢數據時,`DbContext` 會將數據放入內存緩存中。如果相同的數據再次被查詢,它會從緩存中取出來,而不是從資料庫。這可以提高應用程序的性能。
5. **管理關聯性:**
`DbContext` 能夠管理資料庫表之間的關聯(如一對多、多對多等),並能夠方便地表示和操縱這些關聯。
## 註冊服務
在program.cs 中註冊`DbContext`
```csharp=
// Add DbContext with MySQL
services.AddDbContext<TestConnDBContext>(options =>
options.UseMySql(configuration.GetConnectionString("DefaultConnection"),
ServerVersion.AutoDetect(configuration.GetConnectionString("DefaultConnection"))));
```
### 說明
這段程式碼在ASP.NET Core的依賴注入(DI)系統中註冊TestConnDB這個DbContext。 具體來說,它做了以下幾點:
* **依賴注入註冊**: AddDbContext是一個擴充方法,用於將TestConnDB DbContext類別註冊為服務。 這樣,在控制器或其他服務中需要存取資料庫時,TestConnDB實例可以透過建構函式註入自動提供。
* **設定資料庫提供者**: 使用options.UseMySql指定Entity Framework Core使用MySQL作為資料庫提供者。 這裡告訴EF Core用於應用程式的資料庫是MySQL。
* **設定資料庫連線字串**: 透過builder.Configuration.GetConnectionString("DefaultConnection")從設定(通常是appsettings.json檔案或環境變數)取得名為"DefaultConnection"的資料庫連線字串。
* **自動偵測伺服器版本**: ServerVersion.AutoDetect用於自動偵測MySQL伺服器的版本。 這對於EF Core在產生SQL指令時考慮特定版本的資料庫特性和行為很重要。
## appsettings.json
在appsettings.json檔案中,加入以下內容
``` json=
"ConnectionStrings": {
"DefaultConnection": "Server=localhost;Database=TestConn;User Id=root;"
}
```
### 說明
這段 JSON 配置是定義在 ASP.NET Core 應用程式的 appsettings.json 檔案中,用於儲存資料庫連接字串的設定。 它是設定檔中的一部分,讓您可以在不修改程式碼的情況下,指定與資料庫連接有關的資訊。 以下是對這段配置的逐一解釋:
* **"ConnectionStrings"**:這是一個 JSON 物件,包含應用程式中所有資料庫連接字串的設定。 您可以在這裡定義一個或多個連接字串。
* **"DefaultConnection"**:這是連接字串的名稱。 在代碼中,您會通過這個名稱來獲取連接字串的值。 這個名字是自訂的,您可以根據需要命名。
* **"Server=localhost;Database=TestConn;User Id=root;"**:這是一個特定的連接字串,用於定義如何連接到資料庫。 具體來說:
* **Server=localhost**:指定資料庫伺服器的位置。 在這個例子中,它指向本機(localhost),通常用於開發環境。
* **Database=TestConn**:指定要連線的資料庫的名稱。 在這個例子中,資料庫名為 TestConn。
* **User Id=root**:指定用於連接資料庫的使用者名稱。 這裡使用的是 root,通常是MySQL資料庫的預設管理員帳號。
在您的應用程式中,當 Entity Framework Core 或其他資料庫用戶端程式庫嘗試建立資料庫連線時,它們會使用這個連接字串中定義的參數。
您可以透過 configuration.GetConnectionString("DefaultConnection") 這樣的程式碼來取得這個連接字串,並在您的應用程式中使用它,正如之前在 DbContext 的配置中所做的那樣。
## API Controller
```csharp=
using Microsoft.AspNetCore.Mvc;
using Microsoft.EntityFrameworkCore;
using StockBacktesting.Models;
namespace StockBacktesting.Controllers
{
[ApiController]
[Route("[controller]")]
public class ItemsController : ControllerBase
{
private readonly TestConnDBContext _context;
public ItemsController(TestConnDBContext context)
{
_context = context;
}
// 获取所有项目
[HttpGet]
public ActionResult<List<Connection>> GetAll() =>
_context.Connection.ToList();
// 通过ID获取项目
[HttpGet("{id}")]
public ActionResult<Connection> GetById(int id)
{
var item = _context.Connection.Find(id);
if (item == null)
{
return NotFound();
}
return item;
}
// 创建新项目
[HttpPost]
public ActionResult<Connection> Create(Connection connection)
{
_context.Connection.Add(connection);
_context.SaveChanges();
return CreatedAtAction(nameof(GetById), new { id = connection.ConnectionId }, connection);
}
// 更新项目
[HttpPut("{id}")]
public IActionResult Update(int id, Connection connection)
{
if (id != connection.ConnectionId)
{
return BadRequest();
}
_context.Entry(connection).State = EntityState.Modified;
try
{
_context.SaveChanges();
}
catch (DbUpdateConcurrencyException)
{
if (!_context.Connection.Any(e => e.ConnectionId == id))
{
return NotFound();
}
else
{
throw;
}
}
return NoContent();
}
// 删除项目
[HttpDelete("{id}")]
public IActionResult Delete(int id)
{
var connection = _context.Connection.Find(id);
if (connection == null)
{
return NotFound();
}
_context.Connection.Remove(connection);
_context.SaveChanges();
return NoContent();
}
}
}
```