From 4375ca0da885ed2fe3f4fdab28dcf865fc690dc3 Mon Sep 17 00:00:00 2001 From: Suphonchai Phoonsawat Date: Sun, 9 Nov 2025 09:45:52 +0700 Subject: [PATCH 1/8] fix mange to manage.id --- BMA.EHR.Insignia/Controllers/InsigniaManageController.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/BMA.EHR.Insignia/Controllers/InsigniaManageController.cs b/BMA.EHR.Insignia/Controllers/InsigniaManageController.cs index aaf9dffc..67002911 100644 --- a/BMA.EHR.Insignia/Controllers/InsigniaManageController.cs +++ b/BMA.EHR.Insignia/Controllers/InsigniaManageController.cs @@ -791,7 +791,7 @@ namespace BMA.EHR.Insignia.Service.Controllers var insigniaManageOrganiation = await _context.InsigniaManageOrganiations.AsQueryable() .Include(x => x.InsigniaManageProfiles) - .FirstOrDefaultAsync(x => x.OrganizationId == insigniaNoteProfile.RootId && x.InsigniaManage == insigniaManage); + .FirstOrDefaultAsync(x => x.OrganizationId == insigniaNoteProfile.RootId && x.InsigniaManage.Id == insigniaManage.Id); // แก้เป็นหาจากหน่วยงานยืมเพิม manage id if (insigniaManageOrganiation == null) return Error(GlobalMessages.InsigniaManageOrgNotFound); From 5fc3cfa3b4dddd976b82fe388312665d1c3309a4 Mon Sep 17 00:00:00 2001 From: Suphonchai Phoonsawat Date: Sun, 9 Nov 2025 09:58:41 +0700 Subject: [PATCH 2/8] fix #1831 --- .../Repositories/Reports/InsigniaReportRepository.cs | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs b/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs index 19fe5ce4..bbeaf322 100644 --- a/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs +++ b/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs @@ -1583,12 +1583,10 @@ namespace BMA.EHR.Application.Repositories.Reports .AsQueryable() .ToListAsync(); insigniaPeriods = insigniaPeriods - .Where(x => x.StartDate <= DateTime.Now.Date || x.InsigniaRequests.Count == 0).ToList(); + .Where(x => x.StartDate <= DateTime.Now.Date && x.InsigniaRequests.Count == 0).ToList(); foreach (var insigniaPeriod in insigniaPeriods) { - if (insigniaPeriod.StartDate >= DateTime.Now.Date || insigniaPeriod.InsigniaRequests.Count > 0) - continue; var organizations = await _userProfileRepository.GetActiveRootLatestAsync(AccessToken); if (organizations == null) continue; From 36aea81d544320918cd12428bab6658caba30af7 Mon Sep 17 00:00:00 2001 From: Suphonchai Phoonsawat Date: Mon, 10 Nov 2025 15:02:44 +0700 Subject: [PATCH 3/8] change to unauthorize api --- BMA.EHR.Application/Repositories/UserProfileRepository.cs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/BMA.EHR.Application/Repositories/UserProfileRepository.cs b/BMA.EHR.Application/Repositories/UserProfileRepository.cs index a5812b2a..df2fe6b0 100644 --- a/BMA.EHR.Application/Repositories/UserProfileRepository.cs +++ b/BMA.EHR.Application/Repositories/UserProfileRepository.cs @@ -66,7 +66,7 @@ namespace BMA.EHR.Application.Repositories { try { - var apiPath = $"{_configuration["API"]}/org/dotnet/root/officer/{rootId}"; + var apiPath = $"{_configuration["API"]}/org/unauthorize/root/officer/{rootId}"; var apiKey = _configuration["API_KEY"]; @@ -132,7 +132,7 @@ namespace BMA.EHR.Application.Repositories { try { - var apiPath = $"{_configuration["API"]}/org/dotnet/find/employee/position"; + var apiPath = $"{_configuration["API"]}/org/unauthorize/find/employee/position"; var apiKey = _configuration["API_KEY"]; var body = new @@ -1088,7 +1088,7 @@ namespace BMA.EHR.Application.Repositories { try { - var apiPath = $"{_configuration["API"]}/org/active/root/all"; + var apiPath = $"{_configuration["API"]}/org/unauthorize/active/root/all"; var apiKey = _configuration["API_KEY"]; var apiResult = await GetExternalAPIAsync(apiPath, accessToken ?? "", apiKey); From 2187142668a4a715b47f549e4fc31b1fe22449e6 Mon Sep 17 00:00:00 2001 From: Suphonchai Phoonsawat Date: Tue, 11 Nov 2025 05:43:02 +0700 Subject: [PATCH 4/8] fix hangfire --- .../Controllers/InsigniaRequestController.cs | 8 +++++ BMA.EHR.Insignia/Program.cs | 34 +++++++++++++++++-- 2 files changed, 40 insertions(+), 2 deletions(-) diff --git a/BMA.EHR.Insignia/Controllers/InsigniaRequestController.cs b/BMA.EHR.Insignia/Controllers/InsigniaRequestController.cs index dbb553ee..211a651a 100644 --- a/BMA.EHR.Insignia/Controllers/InsigniaRequestController.cs +++ b/BMA.EHR.Insignia/Controllers/InsigniaRequestController.cs @@ -286,6 +286,14 @@ namespace BMA.EHR.Insignia.Service.Controllers #endregion + [HttpGet("test")] + [AllowAnonymous] + public async Task> Test() + { + await _insigniaReportRepository.CalInsigniaRequestBkkByType("officer"); + return Success(); + } + #region " จัดทำรายชื่อครูที่มีสิทธิในการยืนขอเครื่องราชฯ " /// diff --git a/BMA.EHR.Insignia/Program.cs b/BMA.EHR.Insignia/Program.cs index cd3684fe..ea04682f 100644 --- a/BMA.EHR.Insignia/Program.cs +++ b/BMA.EHR.Insignia/Program.cs @@ -184,10 +184,26 @@ var app = builder.Build(); { manager.AddOrUpdate("แจ้งเตือนรอบเครื่องราชฯ", Job.FromExpression(x => x.NotifyInsignia()), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); manager.AddOrUpdate("ล็อกข้อมูลรอบเครื่องราชฯ", Job.FromExpression(x => x.LockInsignia()), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); - manager.AddOrUpdate("คำนวนผู้ได้รับเครื่องราชฯ", Job.FromExpression(x => x.CalInsigniaRequestBkkByType("officer")), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); - manager.AddOrUpdate("คำนวนผู้ได้รับเครื่องราชฯ Employee", Job.FromExpression(x => x.CalInsigniaRequestBkkByType("employee")), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); + //manager.AddOrUpdate("คำนวนผู้ได้รับเครื่องราชฯ", Job.FromExpression(x => x.CalInsigniaRequestBkkByType("officer")), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); + //manager.AddOrUpdate("คำนวนผู้ได้รับเครื่องราชฯ Employee", Job.FromExpression(x => x.CalInsigniaRequestBkkByType("employee")), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); } + RecurringJob.AddOrUpdate( + "คำนวนผู้ได้รับเครื่องราชฯ", + x => x.CalInsigniaRequestBkkByType("officer"), + Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), + Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), + TimeZoneInfo.Local + ); + + RecurringJob.AddOrUpdate( + "คำนวนผู้ได้รับเครื่องราชฯ Employee", + x => x.CalInsigniaRequestBkkByType("employee"), + Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]) + 2, + Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), + TimeZoneInfo.Local + ); + // apply migrations await using var scope = app.Services.CreateAsyncScope(); await using var db = scope.ServiceProvider.GetRequiredService(); @@ -196,9 +212,23 @@ var app = builder.Build(); //var rabbitMQConsumer = app.Services.GetRequiredService(); //rabbitMQConsumer.StartReceiving(); + + app.Run(); } +// เพิ่ม helper method +static async Task ExecuteJobWithScope(string type) +{ + // ใช้ HttpContext current service provider + var scopeFactory = new HttpContextAccessor().HttpContext? + .RequestServices.GetRequiredService(); + + using var scope = scopeFactory.CreateScope(); + var repo = scope.ServiceProvider.GetRequiredService(); + await repo.CalInsigniaRequestBkkByType(type); +} + void ConfigureLogs() { var environment = Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT"); From 998ca38da8e5c7c3b71322f10abeddde81da0bb2 Mon Sep 17 00:00:00 2001 From: Suphonchai Phoonsawat Date: Tue, 11 Nov 2025 09:51:18 +0700 Subject: [PATCH 5/8] change method --- .../Reports/InsigniaReportRepository.cs | 5 ++++ BMA.EHR.Insignia/Program.cs | 24 ++++++------------- 2 files changed, 12 insertions(+), 17 deletions(-) diff --git a/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs b/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs index bbeaf322..bfdd6303 100644 --- a/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs +++ b/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs @@ -1575,6 +1575,11 @@ namespace BMA.EHR.Application.Repositories.Reports } } + public void CalculateInsigniaRequestBkkByType(string type = "officer") + { + CalInsigniaRequestBkkByType(type).GetAwaiter().GetResult(); + } + //คำนวนผู้ได้รับเครื่องราชฯ public async Task CalInsigniaRequestBkkByType(string type = "officer") { diff --git a/BMA.EHR.Insignia/Program.cs b/BMA.EHR.Insignia/Program.cs index ea04682f..5352e7b3 100644 --- a/BMA.EHR.Insignia/Program.cs +++ b/BMA.EHR.Insignia/Program.cs @@ -184,22 +184,22 @@ var app = builder.Build(); { manager.AddOrUpdate("แจ้งเตือนรอบเครื่องราชฯ", Job.FromExpression(x => x.NotifyInsignia()), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); manager.AddOrUpdate("ล็อกข้อมูลรอบเครื่องราชฯ", Job.FromExpression(x => x.LockInsignia()), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); - //manager.AddOrUpdate("คำนวนผู้ได้รับเครื่องราชฯ", Job.FromExpression(x => x.CalInsigniaRequestBkkByType("officer")), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); + //manager.AddOrUpdate("คำนวนผู้ได้รับเครื่องราชฯ", () => CalculateInsigniaRequestBkkByType("officer"), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); //manager.AddOrUpdate("คำนวนผู้ได้รับเครื่องราชฯ Employee", Job.FromExpression(x => x.CalInsigniaRequestBkkByType("employee")), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local); } RecurringJob.AddOrUpdate( "คำนวนผู้ได้รับเครื่องราชฯ", - x => x.CalInsigniaRequestBkkByType("officer"), - Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]), + x => x.CalculateInsigniaRequestBkkByType("officer"), + Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]) - 5, Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local ); - + RecurringJob.AddOrUpdate( "คำนวนผู้ได้รับเครื่องราชฯ Employee", - x => x.CalInsigniaRequestBkkByType("employee"), - Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]) + 2, + x => x.CalculateInsigniaRequestBkkByType("employee"), + Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]) - 4, Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), TimeZoneInfo.Local ); @@ -217,17 +217,7 @@ var app = builder.Build(); app.Run(); } -// เพิ่ม helper method -static async Task ExecuteJobWithScope(string type) -{ - // ใช้ HttpContext current service provider - var scopeFactory = new HttpContextAccessor().HttpContext? - .RequestServices.GetRequiredService(); - - using var scope = scopeFactory.CreateScope(); - var repo = scope.ServiceProvider.GetRequiredService(); - await repo.CalInsigniaRequestBkkByType(type); -} + void ConfigureLogs() { From f081034e36e4741aa8a751bd7268fcbd959dd0d9 Mon Sep 17 00:00:00 2001 From: Suphonchai Phoonsawat Date: Tue, 11 Nov 2025 10:40:49 +0700 Subject: [PATCH 6/8] =?UTF-8?q?fix=20hangfire=20=E0=B9=81=E0=B8=A2?= =?UTF-8?q?=E0=B8=81=20job=20=E0=B8=AD=E0=B8=AD=E0=B8=81=E0=B8=88=E0=B8=B2?= =?UTF-8?q?=E0=B8=81=E0=B8=81=E0=B8=B1=E0=B8=99=20=E0=B9=81=E0=B8=A5?= =?UTF-8?q?=E0=B8=B0=E0=B9=81=E0=B8=81=E0=B9=89=E0=B9=80=E0=B8=A3=E0=B8=B7?= =?UTF-8?q?=E0=B9=88=E0=B8=AD=E0=B8=87=E0=B8=81=E0=B8=B2=E0=B8=A3=E0=B8=AA?= =?UTF-8?q?=E0=B9=88=E0=B8=87=20token?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Repositories/GenericRepository.cs | 1 + .../Repositories/UserProfileRepository.cs | 4 ++-- .../Controllers/InsigniaRequestController.cs | 2 +- BMA.EHR.Insignia/Program.cs | 21 +++++++++++++++---- 4 files changed, 21 insertions(+), 7 deletions(-) diff --git a/BMA.EHR.Application/Repositories/GenericRepository.cs b/BMA.EHR.Application/Repositories/GenericRepository.cs index 1f10ca37..b5519c15 100644 --- a/BMA.EHR.Application/Repositories/GenericRepository.cs +++ b/BMA.EHR.Application/Repositories/GenericRepository.cs @@ -113,6 +113,7 @@ namespace BMA.EHR.Application.Repositories { try { + var json = JsonConvert.SerializeObject(body); var stringContent = new StringContent(json, Encoding.UTF8, "application/json"); //stringContent.Headers.ContentType = new MediaTypeHeaderValue("application/json"); diff --git a/BMA.EHR.Application/Repositories/UserProfileRepository.cs b/BMA.EHR.Application/Repositories/UserProfileRepository.cs index df2fe6b0..2b420e5d 100644 --- a/BMA.EHR.Application/Repositories/UserProfileRepository.cs +++ b/BMA.EHR.Application/Repositories/UserProfileRepository.cs @@ -146,7 +146,7 @@ namespace BMA.EHR.Application.Repositories // สร้าง HTTP content //var body = new StringContent(bodyJson, Encoding.UTF8, "application/json"); - var apiResult = await PostExternalAPIAsync(apiPath, accessToken, body, apiKey); + var apiResult = await PostExternalAPIAsync(apiPath, accessToken ?? "", body, apiKey); if (apiResult != null) { @@ -157,7 +157,7 @@ namespace BMA.EHR.Application.Repositories return null; } - catch + catch(Exception ex) { throw; } diff --git a/BMA.EHR.Insignia/Controllers/InsigniaRequestController.cs b/BMA.EHR.Insignia/Controllers/InsigniaRequestController.cs index 211a651a..005f9882 100644 --- a/BMA.EHR.Insignia/Controllers/InsigniaRequestController.cs +++ b/BMA.EHR.Insignia/Controllers/InsigniaRequestController.cs @@ -290,7 +290,7 @@ namespace BMA.EHR.Insignia.Service.Controllers [AllowAnonymous] public async Task> Test() { - await _insigniaReportRepository.CalInsigniaRequestBkkByType("officer"); + await _insigniaReportRepository.CalInsigniaRequestBkkByType("employee"); return Success(); } diff --git a/BMA.EHR.Insignia/Program.cs b/BMA.EHR.Insignia/Program.cs index 5352e7b3..a4dd716a 100644 --- a/BMA.EHR.Insignia/Program.cs +++ b/BMA.EHR.Insignia/Program.cs @@ -125,9 +125,14 @@ var builder = WebApplication.CreateBuilder(args); DashboardJobListLimit = 50000, TransactionTimeout = TimeSpan.FromMinutes(1), InvisibilityTimeout = TimeSpan.FromHours(3), - TablesPrefix = "Hangfire" + TablesPrefix = "Hangfire_Insignia" }))); - builder.Services.AddHangfireServer(); + builder.Services.AddHangfireServer(options => + { + options.ServerName = "Insignia-Server"; // ← ระบุชื่อ server + options.WorkerCount = 5; // ← + options.Queues = new[] { "insignia" }; // ← worker จะรันเฉพาะ queue "insignia" + }); // RabbitMQ @@ -193,7 +198,11 @@ var app = builder.Build(); x => x.CalculateInsigniaRequestBkkByType("officer"), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]) - 5, Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), - TimeZoneInfo.Local + new RecurringJobOptions + { + TimeZone = TimeZoneInfo.Local, + QueueName = "insignia" // ← กำหนด queue + } ); RecurringJob.AddOrUpdate( @@ -201,7 +210,11 @@ var app = builder.Build(); x => x.CalculateInsigniaRequestBkkByType("employee"), Cron.Daily(Int32.Parse(builder.Configuration["KeycloakCron:Hour"]) - 4, Int32.Parse(builder.Configuration["KeycloakCron:Minute"])), - TimeZoneInfo.Local + new RecurringJobOptions + { + TimeZone = TimeZoneInfo.Local, + QueueName = "insignia" // ← กำหนด queue + } ); // apply migrations From 87c4f85bf6b340d5b5a30064831337806107dd6a Mon Sep 17 00:00:00 2001 From: Suphonchai Phoonsawat Date: Tue, 11 Nov 2025 11:51:22 +0700 Subject: [PATCH 7/8] =?UTF-8?q?fix=20=E0=B8=81=E0=B8=B2=E0=B8=A3=E0=B8=99?= =?UTF-8?q?=E0=B8=B1=E0=B8=9A=E0=B8=88=E0=B8=B3=E0=B8=99=E0=B8=A7=E0=B8=99?= =?UTF-8?q?=20=E0=B8=95=E0=B9=89=E0=B8=AD=E0=B8=87=E0=B9=81=E0=B8=A2?= =?UTF-8?q?=E0=B8=81=20officer=20+=20employee?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Repositories/Reports/InsigniaReportRepository.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs b/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs index bfdd6303..1e0dcac7 100644 --- a/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs +++ b/BMA.EHR.Application/Repositories/Reports/InsigniaReportRepository.cs @@ -1588,7 +1588,7 @@ namespace BMA.EHR.Application.Repositories.Reports .AsQueryable() .ToListAsync(); insigniaPeriods = insigniaPeriods - .Where(x => x.StartDate <= DateTime.Now.Date && x.InsigniaRequests.Count == 0).ToList(); + .Where(x => x.StartDate <= DateTime.Now.Date && x.InsigniaRequests.Where(x => x.ProfileType!.ToLower().Trim() == type.Trim().ToLower()).Count() == 0).ToList(); foreach (var insigniaPeriod in insigniaPeriods) { From 3fd9d05cd2c0d9909b1915a5a2c3f33be92799f8 Mon Sep 17 00:00:00 2001 From: Adisak Date: Tue, 11 Nov 2025 12:03:14 +0700 Subject: [PATCH 8/8] #1820 --- .../Controllers/RetirementResignEmployeeController.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/BMA.EHR.Retirement.Service/Controllers/RetirementResignEmployeeController.cs b/BMA.EHR.Retirement.Service/Controllers/RetirementResignEmployeeController.cs index d5b7037d..3f1e0cdc 100644 --- a/BMA.EHR.Retirement.Service/Controllers/RetirementResignEmployeeController.cs +++ b/BMA.EHR.Retirement.Service/Controllers/RetirementResignEmployeeController.cs @@ -2364,6 +2364,7 @@ namespace BMA.EHR.Retirement.Service.Controllers commandCode = r.commandCode, commandName = r.commandName, remark = r.remark, + resignId = p.Id, }).ToList(); var baseAPIOrg = _configuration["API"];