diff --git a/Document/10_TODO.md b/Document/10_TODO.md
index 9190463..ddb4c41 100644
--- a/Document/10_TODO.md
+++ b/Document/10_TODO.md
@@ -17,9 +17,9 @@
- [x] 登录防刷限流(MiniApi)
## C. 多租户与参数字典
-- [ ] 多租户中间件:从 Header/域名解析租户(Shared.Web + Tenancy)
-- [ ] EF Core 全局查询过滤(tenant_id)
-- [ ] 参数字典模块(系统参数/业务参数)CRUD 与缓存(Dictionary 模块)
+- [x] 多租户中间件:从 Header/域名解析租户(Shared.Web + Tenancy)
+- [x] EF Core 全局查询过滤(tenant_id)
+- [x] 参数字典模块(系统参数/业务参数)CRUD 与缓存(Dictionary 模块)
## D. 数据访问与多数据源
- [ ] EF Core 10 基础上下文、实体基类、审计字段
diff --git a/src/Api/TakeoutSaaS.AdminApi/Controllers/DictionaryController.cs b/src/Api/TakeoutSaaS.AdminApi/Controllers/DictionaryController.cs
new file mode 100644
index 0000000..7232ed2
--- /dev/null
+++ b/src/Api/TakeoutSaaS.AdminApi/Controllers/DictionaryController.cs
@@ -0,0 +1,126 @@
+using Microsoft.AspNetCore.Authorization;
+using Microsoft.AspNetCore.Mvc;
+using TakeoutSaaS.Application.Dictionary.Abstractions;
+using TakeoutSaaS.Application.Dictionary.Contracts;
+using TakeoutSaaS.Application.Dictionary.Models;
+using TakeoutSaaS.Module.Authorization.Attributes;
+using TakeoutSaaS.Shared.Abstractions.Results;
+using TakeoutSaaS.Shared.Web.Api;
+
+namespace TakeoutSaaS.AdminApi.Controllers;
+
+///
+/// 参数字典管理。
+///
+[ApiVersion("1.0")]
+[Authorize]
+[Route("api/admin/v{version:apiVersion}/dictionaries")]
+public sealed class DictionaryController : BaseApiController
+{
+ private readonly IDictionaryAppService _dictionaryAppService;
+
+ ///
+ /// 初始化字典控制器。
+ ///
+ /// 字典服务
+ public DictionaryController(IDictionaryAppService dictionaryAppService)
+ {
+ _dictionaryAppService = dictionaryAppService;
+ }
+
+ ///
+ /// 查询字典分组。
+ ///
+ [HttpGet]
+ [PermissionAuthorize("dictionary:group:read")]
+ [ProducesResponseType(typeof(ApiResponse>), StatusCodes.Status200OK)]
+ public async Task>> GetGroups([FromQuery] DictionaryGroupQuery query, CancellationToken cancellationToken)
+ {
+ var groups = await _dictionaryAppService.SearchGroupsAsync(query, cancellationToken);
+ return ApiResponse>.Ok(groups);
+ }
+
+ ///
+ /// 创建字典分组。
+ ///
+ [HttpPost]
+ [PermissionAuthorize("dictionary:group:create")]
+ [ProducesResponseType(typeof(ApiResponse), StatusCodes.Status200OK)]
+ public async Task> CreateGroup([FromBody] CreateDictionaryGroupRequest request, CancellationToken cancellationToken)
+ {
+ var group = await _dictionaryAppService.CreateGroupAsync(request, cancellationToken);
+ return ApiResponse.Ok(group);
+ }
+
+ ///
+ /// 更新字典分组。
+ ///
+ [HttpPut("{groupId:guid}")]
+ [PermissionAuthorize("dictionary:group:update")]
+ [ProducesResponseType(typeof(ApiResponse), StatusCodes.Status200OK)]
+ public async Task> UpdateGroup(Guid groupId, [FromBody] UpdateDictionaryGroupRequest request, CancellationToken cancellationToken)
+ {
+ var group = await _dictionaryAppService.UpdateGroupAsync(groupId, request, cancellationToken);
+ return ApiResponse.Ok(group);
+ }
+
+ ///
+ /// 删除字典分组。
+ ///
+ [HttpDelete("{groupId:guid}")]
+ [PermissionAuthorize("dictionary:group:delete")]
+ [ProducesResponseType(typeof(ApiResponse