Initial commit: HealthManager full-stack health management platform
Backend: .NET 10 + PostgreSQL + EF Core + JWT + SignalR Frontend patient: React 19 + TypeScript + Vite (mobile H5) Frontend doctor: React 19 + TypeScript + Vite (desktop web)
This commit is contained in:
@@ -0,0 +1,61 @@
|
||||
using System.Security.Claims;
|
||||
using System.Text.Json;
|
||||
using HealthManager.Application.Services;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
|
||||
namespace HealthManager.WebApi.Controllers;
|
||||
|
||||
[ApiController]
|
||||
[Route("api/health-records")]
|
||||
[Authorize]
|
||||
public class HealthController(HealthService healthService) : ControllerBase
|
||||
{
|
||||
private Guid UserId => Guid.Parse(User.FindFirstValue(ClaimTypes.NameIdentifier)!);
|
||||
private string Role => User.FindFirstValue(ClaimTypes.Role)!;
|
||||
|
||||
[HttpGet]
|
||||
public async Task<IActionResult> GetRecords([FromQuery] string? type, [FromQuery] int days = 30)
|
||||
{
|
||||
var targetUserId = UserId;
|
||||
|
||||
// Doctors can query any patient
|
||||
if (Role == "doctor" && Request.Query.ContainsKey("patientId"))
|
||||
targetUserId = Guid.Parse(Request.Query["patientId"]!);
|
||||
|
||||
var records = await healthService.GetRecordsAsync(targetUserId, type, days);
|
||||
return Ok(records.Select(r => new
|
||||
{
|
||||
r.Id, r.Type, Value = r.Value.RootElement.GetRawText(), r.Unit,
|
||||
r.RecordedAt, r.Source, r.Notes, r.CreatedAt,
|
||||
}));
|
||||
}
|
||||
|
||||
[HttpGet("stats")]
|
||||
public async Task<IActionResult> GetStats()
|
||||
{
|
||||
var stats = await healthService.GetStatsAsync(UserId);
|
||||
return Ok(stats);
|
||||
}
|
||||
|
||||
[HttpGet("latest/{type}")]
|
||||
public async Task<IActionResult> GetLatest(string type)
|
||||
{
|
||||
var record = await healthService.GetLatestAsync(UserId, type);
|
||||
if (record == null) return Ok((object?)null);
|
||||
return Ok(new { record.Id, record.Type, Value = record.Value.RootElement.GetRawText(), record.Unit, record.RecordedAt, record.Source });
|
||||
}
|
||||
|
||||
[HttpPost]
|
||||
public async Task<IActionResult> AddRecord([FromBody] HealthRecordCreateRequest request)
|
||||
{
|
||||
// Validate JSON
|
||||
try { JsonDocument.Parse(request.ValueJson); }
|
||||
catch (JsonException) { return BadRequest(new { message = "无效的数据格式" }); }
|
||||
|
||||
var record = await healthService.AddRecordAsync(UserId, request.Type, request.ValueJson, request.Unit, request.RecordedAt, request.Notes);
|
||||
return Ok(new { record.Id, record.Type, Value = record.Value.RootElement.GetRawText(), record.Unit, record.RecordedAt, record.Source });
|
||||
}
|
||||
}
|
||||
|
||||
public record HealthRecordCreateRequest(string Type, string ValueJson, string Unit, DateTime RecordedAt, string? Notes);
|
||||
Reference in New Issue
Block a user