添加服务器负载展示,修正部分变量命名,补全缺失的代码注释信息

This commit is contained in:
root 2024-11-24 14:42:06 +08:00
parent 8a324fc2c3
commit d62662b36e
11 changed files with 222 additions and 48 deletions

View file

@ -20,22 +20,22 @@ namespace iFileProxy.Controllers
{
return taskManager.AddTask(HttpContext) switch
{
TaskAddState.Success => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.Success, message = "succ" }),
TaskAddState.Fail => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.Fail, message = "unkown error!" }),
TaskAddState.ErrUrlRepeat => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrUrlRepeat, message = "此url已经在任务队列中,请勿重复提交" }),
TaskAddState.ErrTaskIdRepeat => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrTaskIdRepeat, message = "TaskIdRepeat!!!" }),
TaskAddState.ErrUrlInvalid => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrUrlInvalid, message = "非法Url" }),
TaskAddState.ErrDbFail => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrDbFail, message = "数据库数据提交失败!" }),
TaskAddState.ErrMaxParallelTasksLimit => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrMaxParallelTasksLimit, message = "服务端并行数量达到上限!" }),
TaskAddState.ErrFileSizeLimit => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrFileSizeLimit, message = "指定的文件大小超过系统最大限制!" }),
TaskAddState.ErrFileNameForbidden => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrFileNameForbidden, message = "文件名非法!" }),
TaskAddState.ErrIPForbidden => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrIPForbidden, message = "请求次数超过限制!" }),
TaskAddState.ErrTargetHostForbidden => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrTargetHostForbidden, message = "目标主机不在服务白名单内!" }),
TaskAddState.ErrGetFileInfo => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrGetFileInfo, message = "目标文件信息获取失败!" }),
TaskAddState.ErrQueueLengthLimit => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.ErrQueueLengthLimit, message = "服务器任务队列已满 请稍候重试!" }),
TaskAddState.Pending => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.Pending, message = "已经添加到任务队列!" }),
TaskAddState.Success => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.Success, Message = "succ" }),
TaskAddState.Fail => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.Fail, Message = "unkown error!" }),
TaskAddState.ErrUrlRepeat => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrUrlRepeat, Message = "此url已经在任务队列中,请勿重复提交" }),
TaskAddState.ErrTaskIdRepeat => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrTaskIdRepeat, Message = "TaskIdRepeat!!!" }),
TaskAddState.ErrUrlInvalid => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrUrlInvalid, Message = "非法Url" }),
TaskAddState.ErrDbFail => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrDbFail, Message = "数据库数据提交失败!" }),
TaskAddState.ErrMaxParallelTasksLimit => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrMaxParallelTasksLimit, Message = "服务端并行数量达到上限!" }),
TaskAddState.ErrFileSizeLimit => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrFileSizeLimit, Message = "指定的文件大小超过系统最大限制!" }),
TaskAddState.ErrFileNameForbidden => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrFileNameForbidden, Message = "文件名非法!" }),
TaskAddState.ErrIPForbidden => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrIPForbidden, Message = "请求次数超过限制!" }),
TaskAddState.ErrTargetHostForbidden => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrTargetHostForbidden, Message = "目标主机不在服务白名单内!" }),
TaskAddState.ErrGetFileInfo => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrGetFileInfo, Message = "目标文件信息获取失败!" }),
TaskAddState.ErrQueueLengthLimit => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.ErrQueueLengthLimit, Message = "服务器任务队列已满 请稍候重试!" }),
TaskAddState.Pending => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.Pending, Message = "已经添加到任务队列!" }),
_ => (ActionResult<CommonRsp>)Ok(new CommonRsp() { retcode = (int)TaskAddState.Success, message = "succ default" }),
_ => (ActionResult<CommonRsp>)Ok(new CommonRsp() { Retcode = (int)TaskAddState.Success, Message = "succ default" }),
};
}
@ -52,7 +52,14 @@ namespace iFileProxy.Controllers
d.QueuePosition = taskManager.GetQueuePosition(d.TaskId);
}
}
return Ok(new CommonRsp() { retcode = 0, data = data ,message = "succ" });
return Ok(new CommonRsp() { Retcode = 0, Data = data ,Message = "succ" });
}
[HttpPost]
[HttpGet]
[Route("/GetServerLoad")]
public ActionResult<CommonRsp> GetServerLoad() {
return Ok(new CommonRsp { Retcode = 0, Message = "succ", Data = taskManager.GetServerTaskLoadInfo() });
}
[HttpGet]
@ -75,12 +82,12 @@ namespace iFileProxy.Controllers
fileName = d.Where(x => x.TaskId == taskID).FirstOrDefault()?.FileName;
}
if (fileName == null)
return Ok(new CommonRsp() { message = "file not exists", retcode = -1 });
return Ok(new CommonRsp() { Message = "file not exists", Retcode = -1 });
var filePath = Path.Combine(AppConfig.GetCurrConfig().DownloadOptions.SavePath, fileName);
if (!System.IO.File.Exists(filePath))
{
return Ok(new CommonRsp() { message = "file not exists", retcode = 1 });
return Ok(new CommonRsp() { Message = "file not exists", Retcode = 1 });
}
// 获取文件的 MIME 类型
var provider = new FileExtensionContentTypeProvider();
@ -96,7 +103,7 @@ namespace iFileProxy.Controllers
// 返回文件内容
return File(fileContents, contentType, Path.GetFileName(filePath));
}
return Ok(new CommonRsp() { message = "task_id not exists", retcode = -1 });
return Ok(new CommonRsp() { Message = "task_id not exists", Retcode = -1 });
}
}

View file

@ -14,7 +14,7 @@ namespace iFileProxy.Helpers
AppConfig _appConfig;
private readonly static Serilog.ILogger _logger = Log.Logger.ForContext<DatabaseHelper>();
Dictionary<string, DB> _dbDictionary = new Dictionary<string, DB>();
Dictionary<string, DB> _dbDictionary = [];
public DatabaseHelper(AppConfig appConfig)
{
@ -245,12 +245,12 @@ namespace iFileProxy.Helpers
}
public bool UpdateFieldsData(string fieldsName, string key,string val)
{
string sql = $"UPDATE t_tasks_info set `{fieldsName}` = @data WHERE `tid` = @tid";
string sql = $"UPDATE t_tasks_info set `{fieldsName}` = @Data WHERE `tid` = @tid";
MySqlConnection conn = GetAndOpenDBConn("iFileProxy_Db");
try
{
using MySqlCommand sqlCmd = new(sql, conn);
sqlCmd.Parameters.AddWithValue("@data",val);
sqlCmd.Parameters.AddWithValue("@Data",val);
sqlCmd.Parameters.AddWithValue("@tid",key);
if (sqlCmd.ExecuteNonQuery() == 1)
{
@ -261,7 +261,7 @@ namespace iFileProxy.Helpers
}
catch (Exception)
{
_logger.Fatal($"Task data update error.");
_logger.Fatal($"Task Data update error.");
throw;
}
finally

View file

@ -45,6 +45,11 @@ namespace iFileProxy.Helpers
return randomNumber;
}
/// <summary>
/// 获取客户端IP地址
/// </summary>
/// <param name="c">HttpContext</param>
/// <returns></returns>
public static string? GetClientIPAddr(HttpContext c)
{
// 尝试从 X-Forwarded-For 请求头获取客户端IP地址
@ -57,6 +62,11 @@ namespace iFileProxy.Helpers
return clientIp;
}
/// <summary>
/// 检查要下载的文件是否存在
/// </summary>
/// <param name="fileName"></param>
/// <returns></returns>
public static bool CheckDownloadFileExists(string fileName)
{
if (File.Exists(Path.Combine(AppConfig.GetCurrConfig().DownloadOptions.SavePath,fileName)))
@ -64,6 +74,12 @@ namespace iFileProxy.Helpers
return false;
}
/// <summary>
/// 获取文件哈希
/// </summary>
/// <param name="fileName">文件路径</param>
/// <param name="algorithm">哈希算法</param>
/// <returns></returns>
public static string GetFileHash(string fileName, FileHashAlgorithm algorithm)
{
byte[] hash = [];

View file

@ -31,7 +31,7 @@ namespace iFileProxy
if (context.Response.StatusCode == 404)
{
context.Response.ContentType = "application/json";
await context.Response.WriteAsync(JsonSerializer.Serialize(new CommonRsp { retcode = 404, message = "this route not exists." }));
await context.Response.WriteAsync(JsonSerializer.Serialize(new CommonRsp { Retcode = 404, Message = "this route not exists." }));
}
}
@ -63,7 +63,7 @@ namespace iFileProxy
context.Response.ContentType = "application/json";
context.Response.StatusCode = (int)code;
return context.Response.WriteAsync(JsonSerializer.Serialize(new CommonRsp { retcode = 1, message = "server internal error" }));
return context.Response.WriteAsync(JsonSerializer.Serialize(new CommonRsp { Retcode = 1, Message = "server internal error" }));
}
}
}

View file

@ -56,7 +56,7 @@
{
context.Response.StatusCode = 200;
context.Response.ContentType = "application/json";
await context.Response.WriteAsync(JsonSerializer.Serialize(new CommonRsp { retcode = 403, message = "请求次数超过限制!" }));
await context.Response.WriteAsync(JsonSerializer.Serialize(new CommonRsp { Retcode = 403, Message = "请求次数超过限制!" }));
return;
}
_IPAccessCountDict[dateStr][ipStr]++;

View file

@ -1,9 +1,12 @@
namespace iFileProxy.Models
{
/// <summary>
/// 通用Http Response
/// </summary>
public class CommonRsp
{
public string message { get; set; }
public object data { get; set; }
public int retcode { get; set; }
public string Message { get; set; } = "def msg";
public object Data { get; set; } = new object();
public int Retcode { get; set; }
}
}

14
src/Models/Security.cs Normal file
View file

@ -0,0 +1,14 @@
namespace iFileProxy.Models
{
/// <summary>
/// 计算文件Hash类型
/// </summary>
public enum FileHashAlgorithm
{
MD5,
SHA1,
SHA256,
SHA384,
SHA512,
}
}

View file

@ -1,40 +1,121 @@
namespace iFileProxy.Models
{
public enum TaskState {
NoInit = 0, // 还未初始化
Running = 1, // 正在进行
Error = 2, // 任务执行时候发生错误 已经结束
End = 3, // 任务正常结束
Cached = 4, // 要下载的内容已经缓存
Cleaned =5, // 内容过期已被清理
Queuing = 6, // 正在排队
/// <summary>
/// 任务状态
/// </summary>
public enum TaskState {
/// <summary>
/// 还未初始化
/// </summary>
NoInit = 0,
/// <summary>
/// 正在进行
/// </summary>
Running = 1,
/// <summary>
/// 任务执行时候发生错误 已经结束
/// </summary>
Error = 2,
/// <summary>
/// 任务正常结束
/// </summary>
End = 3,
/// <summary>
/// 要下载的内容已经缓存
/// </summary>
Cached = 4,
/// <summary>
/// 内容过期已被清理
/// </summary>
Cleaned = 5,
/// <summary>
/// 正在排队
/// </summary>
Queuing = 6,
}
/// <summary>
/// 任务添加状态
/// </summary>
public enum TaskAddState {
/// <summary>
/// 成功
/// </summary>
Success = 0,
/// <summary>
/// 失败
/// </summary>
Fail = 1,
/// <summary>
/// Url重复
/// </summary>
ErrUrlRepeat = 2,
/// <summary>
/// taskId重复
/// </summary>
ErrTaskIdRepeat = 3,
/// <summary>
/// Url无效
/// </summary>
ErrUrlInvalid = 4,
/// <summary>
/// 数据库过程失败
/// </summary>
ErrDbFail = 5,
/// <summary>
/// 并行任务达到设定最大值
/// </summary>
ErrMaxParallelTasksLimit = 6,
/// <summary>
/// 文件大小达到设定最大值
/// </summary>
ErrFileSizeLimit = 7,
/// <summary>
/// 指定的主机已经被管理员拉入黑名单
/// </summary>
ErrTargetHostForbidden = 8,
/// <summary>
/// 禁止的文件名
/// </summary>
ErrFileNameForbidden = 9,
/// <summary>
/// 来访者IP被管理员拉入黑名单
/// </summary>
ErrIPForbidden = 10,
/// <summary>
/// 获取下载信息时候出现错误
/// </summary>
ErrGetFileInfo = 11,
/// <summary>
/// 正在等待任务执行
/// </summary>
Pending = 12,
/// <summary>
/// 队列大小达到设定最大值
/// </summary>
ErrQueueLengthLimit = 13,
}
public enum FileHashAlgorithm
{
MD5,
SHA1,
SHA256,
SHA384,
SHA512,
}
public class DownloadFileInfo {
/// <summary>
/// 文件名
/// </summary>
public string FileName { get; set; }
/// <summary>
/// 文件大小
/// </summary>
public long Size { get; set; }
}
/// <summary>
/// 任务负载信息
/// </summary>
public class ServerTaskLoadInfo {
/// <summary>
/// 正在运行的任务数
/// </summary>
public int Running { get; set; }
/// <summary>
/// 正在队列中的任务数
/// </summary>
public int Queuing { get; set; }
}
}

View file

@ -20,11 +20,15 @@ namespace iFileProxy.Services
private readonly DatabaseHelper _dbHelper;
private readonly int CACHE_LIFETIME;
/// <summary>
/// 缓存管理器
/// </summary>
public LocalCacheManager()
{
_logger.Information("Initializing LocalCacheManager.");
CACHE_LIFETIME = _appConfig.DownloadOptions.CacheLifetime;
_dbHelper = new DatabaseHelper(_appConfig);
// 开始定时清理任务
_timer = new Timer(CheckAndCleanCache, null, TimeSpan.FromSeconds(6), TimeSpan.FromSeconds(60));
_logger.Information("succ.");
}

View file

@ -41,7 +41,7 @@ namespace iFileProxy.Services
for (int i = 0; i < add_task_num; i++) // 运行的任务中不足最大并行数并且有正在队列的task时候添加足够多的任务
{
TaskInfo nextTask = _pendingTasks.Dequeue();
Task.Run(() => StartTask(nextTask)).ConfigureAwait(false);
Task.Run(() => StartTaskAsync(nextTask)).ConfigureAwait(false);
}
}
}
@ -155,6 +155,12 @@ namespace iFileProxy.Services
}
/// <summary>
/// 添加任务信息到数据库并开始任务
/// </summary>
/// <param name="taskInfo">任务信息</param>
/// <param name="queuing">是否正在排队 若正在排队则不开始任务 等待任务调度</param>
/// <returns></returns>
public TaskAddState AddTaskInfoToDb(TaskInfo taskInfo, bool queuing = false)
{
if (_dbHelper.InsertTaskData(taskInfo))
@ -163,7 +169,7 @@ namespace iFileProxy.Services
{
if (taskInfo.Status != TaskState.Cached)
{
StartTask(taskInfo);
StartTaskAsync(taskInfo);
taskInfo.Status = TaskState.Running;
}
_logger.Debug($"[TaskId: {taskInfo.TaskId}] Add to Database Successful.");
@ -180,7 +186,12 @@ namespace iFileProxy.Services
return TaskAddState.ErrDbFail;
}
public async Task StartTask(TaskInfo taskInfo)
/// <summary>
/// 开始任务
/// </summary>
/// <param name="taskInfo">任务信息</param>
/// <returns></returns>
public async Task StartTaskAsync(TaskInfo taskInfo)
{
if (_runningTasks.ContainsKey(taskInfo.TaskId))
{
@ -262,12 +273,22 @@ namespace iFileProxy.Services
_logger.Debug($"[TaskId: {c.StartInfo.Environment["TaskId"]}] {e.Data}");
}
/// <summary>
/// 基于IP地址查询下载列表
/// </summary>
/// <param name="c"></param>
/// <returns></returns>
public List<TaskInfo> GetTaskListByIpAddr(HttpContext c)
{
string? clientIp = MasterHelper.GetClientIPAddr(c);
return JsonSerializer.Deserialize<List<TaskInfo>>(_dbHelper.GetTaskListByIP(clientIp)) ?? [];
}
/// <summary>
/// 获取任务信息
/// </summary>
/// <param name="taskId"></param>
/// <returns></returns>
public List<TaskInfo> GetTaskInfo(string taskId)
{
_logger.Debug(_dbHelper.GetTaskInfoByTid(taskId));
@ -276,6 +297,11 @@ namespace iFileProxy.Services
public Dictionary<string, TaskInfo> GetRunningTasks() => _runningTasks;
/// <summary>
/// 获取task在队列中的位置
/// </summary>
/// <param name="taskId"></param>
/// <returns></returns>
public int GetQueuePosition(string taskId)
{
int position = -1; // 默认值表示未找到
@ -296,6 +322,15 @@ namespace iFileProxy.Services
return position;
}
/// <summary>
/// 获取服务器任务负载信息
/// </summary>
/// <returns></returns>
public ServerTaskLoadInfo GetServerTaskLoadInfo()
{
return new ServerTaskLoadInfo { Queuing = _pendingTasks.Count , Running = _runningTasks.Count};
}
//public bool DeleteTask(HttpContext c)
//{

View file

@ -42,6 +42,8 @@
</div>
<br />
<hr />
<p class="more-content">运行中任务: <span id="running_count">0</span> 排队中任务:<span
id="queuing_count">0</span></p>
<p class="more-content"><a href="/query_download_task.html">查询文件下载任务状态</a> | 捐赠</p>
</div>
</div>
@ -74,6 +76,18 @@
}
});
});
// 加载服务器负载信息
$.ajax({
type: "GET",
url: "/GetServerLoad",
dataType: "json",
success: function (response) {
if (response.retcode == 0) {
running_count.textContent = response.data.running;
queuing_count.textContent = response.data.queuing;
}
}
});
});
</script>