feat: React 프론트엔드 기능 대폭 확장

- 월별근무표: 휴일/근무일 관리, 자동 초기화
- 메일양식: 템플릿 CRUD, To/CC/BCC 설정
- 그룹정보: 부서 관리, 비트 연산 기반 권한 설정
- 업무일지: 수정 성공 메시지 제거, 오늘 근무시간 필터링 수정
- 웹소켓 메시지 type 충돌 버그 수정

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
backuppc
2025-11-27 17:25:31 +09:00
parent b57af6dad7
commit c9b5d756e1
65 changed files with 14028 additions and 467 deletions

View File

@@ -0,0 +1,290 @@
using System;
using System.Linq;
using Newtonsoft.Json;
using FCOMMON;
namespace Project.Web
{
public partial class MachineBridge
{
#region User API
/// <summary>
/// 현재 로그인한 사용자 정보 조회
/// </summary>
public string GetCurrentUserInfo()
{
try
{
if (string.IsNullOrEmpty(info.Login.no))
{
return JsonConvert.SerializeObject(new { Success = false, Message = "로그인이 필요합니다." });
}
var taUser = new dsMSSQLTableAdapters.UsersTableAdapter();
var taGUser = new dsMSSQLTableAdapters.EETGW_GroupUserTableAdapter();
var drUser = taUser.GetID(info.Login.no).FirstOrDefault();
var drGUser = taGUser.GetbyID(info.Login.gcode, info.Login.no).FirstOrDefault();
if (drUser == null)
{
return JsonConvert.SerializeObject(new { Success = false, Message = "사용자 정보를 찾을 수 없습니다." });
}
var userInfo = new
{
Id = drUser.id,
NameK = drUser.name,
NameE = drUser.nameE,
Dept = drUser.dept,
Grade = drUser.grade,
Email = drUser.email,
Tel = drUser.tel,
Hp = drUser.hp,
DateIn = drUser.indate,
DateO = drUser.outdate,
Memo = drUser.memo,
Process = drGUser?.Process ?? "",
State = drGUser?.state ?? "",
UseJobReport = drGUser != null && !drGUser.IsuseJobReportNull() && drGUser.useJobReport,
UseUserState = drGUser != null && !drGUser.IsuseUserStateNull() && drGUser.useUserState,
ExceptHoly = drGUser != null && !drGUser.IsexceptHolyNull() && drGUser.exceptHoly,
Level = drGUser?.level ?? 0
};
return JsonConvert.SerializeObject(new { Success = true, Data = userInfo });
}
catch (Exception ex)
{
return JsonConvert.SerializeObject(new { Success = false, Message = "사용자 정보 조회 실패: " + ex.Message });
}
}
/// <summary>
/// 사용자 정보 조회 (ID로)
/// </summary>
public string GetUserInfoById(string userId)
{
try
{
if (string.IsNullOrEmpty(userId))
{
return JsonConvert.SerializeObject(new { Success = false, Message = "사용자 ID를 입력하세요." });
}
var taUser = new dsMSSQLTableAdapters.UsersTableAdapter();
var taGUser = new dsMSSQLTableAdapters.EETGW_GroupUserTableAdapter();
var drUser = taUser.GetID(userId).FirstOrDefault();
var drGUser = taGUser.GetbyID(info.Login.gcode, userId).FirstOrDefault();
if (drUser == null)
{
return JsonConvert.SerializeObject(new { Success = false, Message = "등록된 사용자가 없습니다." });
}
var userInfo = new
{
Id = drUser.id,
NameK = drUser.name,
NameE = drUser.nameE,
Dept = drUser.dept,
Grade = drUser.grade,
Email = drUser.email,
Tel = drUser.tel,
Hp = drUser.hp,
DateIn = drUser.indate,
DateO = drUser.outdate,
Memo = drUser.memo,
Process = drGUser?.Process ?? "",
State = drGUser?.state ?? "",
UseJobReport = drGUser != null && !drGUser.IsuseJobReportNull() && drGUser.useJobReport,
UseUserState = drGUser != null && !drGUser.IsuseUserStateNull() && drGUser.useUserState,
ExceptHoly = drGUser != null && !drGUser.IsexceptHolyNull() && drGUser.exceptHoly,
Level = drGUser?.level ?? 0
};
return JsonConvert.SerializeObject(new { Success = true, Data = userInfo });
}
catch (Exception ex)
{
return JsonConvert.SerializeObject(new { Success = false, Message = "사용자 정보 조회 실패: " + ex.Message });
}
}
/// <summary>
/// 사용자 정보 저장
/// </summary>
public string SaveUserInfo(string jsonData)
{
try
{
var userData = JsonConvert.DeserializeObject<UserInfoData>(jsonData);
if (userData == null)
{
return JsonConvert.SerializeObject(new { Success = false, Message = "잘못된 데이터 형식입니다." });
}
var gcode = info.Login.gcode;
var uid = userData.Id;
// 현재 사용자 권한 확인
int curLevel = Math.Max(info.Login.level, DBM.getAuth(DBM.eAuthType.account));
// 그룹 사용자 정보 처리
var taUserGrp = new dsMSSQLTableAdapters.EETGW_GroupUserTableAdapter();
var dtUserGrp = taUserGrp.GetData(gcode);
var drGuser = dtUserGrp.Where(t => t.uid == uid).FirstOrDefault();
if (drGuser != null)
{
drGuser.Process = userData.Process ?? "";
drGuser.state = userData.State ?? "";
if (curLevel > 4)
{
drGuser.useJobReport = userData.UseJobReport;
drGuser.useUserState = userData.UseUserState;
drGuser.exceptHoly = userData.ExceptHoly;
}
}
else
{
drGuser = dtUserGrp.NewEETGW_GroupUserRow();
drGuser.wuid = info.Login.no;
drGuser.wdate = DateTime.Now;
drGuser.gcode = gcode;
drGuser.level = 1;
drGuser.uid = uid;
drGuser.state = userData.State ?? "";
drGuser.Process = userData.Process ?? "";
drGuser.useJobReport = userData.UseJobReport;
drGuser.useUserState = userData.UseUserState;
drGuser.exceptHoly = userData.ExceptHoly;
dtUserGrp.AddEETGW_GroupUserRow(drGuser);
}
// 사용자 정보 처리
var tauser = new dsMSSQLTableAdapters.UsersTableAdapter();
var dtuser = tauser.GetID(uid);
var drUser = dtuser.FirstOrDefault();
if (drUser == null)
{
drUser = dtuser.NewUsersRow();
drUser.wuid = info.Login.no;
drUser.wdate = DateTime.Now;
drUser.gcode = gcode;
drUser.level = 1;
drUser.id = uid;
drUser.password = "B6589FC6AB0DC82CF12099D1C2D40AB994E8410C"; // 기본값 0
dtuser.AddUsersRow(drUser);
}
drUser.name = userData.NameK ?? "";
drUser.nameE = userData.NameE ?? "";
drUser.dept = userData.Dept ?? "";
drUser.email = userData.Email ?? "";
drUser.tel = userData.Tel ?? "";
drUser.hp = userData.Hp ?? "";
drUser.indate = userData.DateIn ?? "";
drUser.outdate = userData.DateO ?? "";
drUser.memo = userData.Memo ?? "";
drUser.processs = userData.Process ?? "";
drUser.grade = userData.Grade ?? "";
drUser.EndEdit();
var cnt1 = taUserGrp.Update(dtUserGrp);
var cnt2 = tauser.Update(dtuser);
taUserGrp.Dispose();
tauser.Dispose();
return JsonConvert.SerializeObject(new { Success = true, Message = "저장되었습니다." });
}
catch (Exception ex)
{
return JsonConvert.SerializeObject(new { Success = false, Message = "저장 실패: " + ex.Message });
}
}
/// <summary>
/// 비밀번호 변경
/// </summary>
public string ChangePassword(string oldPassword, string newPassword)
{
try
{
if (string.IsNullOrEmpty(info.Login.no))
{
return JsonConvert.SerializeObject(new { Success = false, Message = "로그인이 필요합니다." });
}
if (string.IsNullOrEmpty(newPassword))
{
return JsonConvert.SerializeObject(new { Success = false, Message = "새 비밀번호를 입력하세요." });
}
var uid = info.Login.no;
int curLevel = Math.Max(info.Login.level, DBM.getAuth(DBM.eAuthType.account));
var taUser = new dsMSSQLTableAdapters.UsersTableAdapter();
var dtUser = taUser.GetID(uid);
var drUser = dtUser.FirstOrDefault();
if (drUser == null)
{
return JsonConvert.SerializeObject(new { Success = false, Message = "사용자 정보를 찾을 수 없습니다." });
}
// 관리자가 아니면 기존 암호 확인
if (curLevel < 5)
{
var encOldPass = Pub.MakePasswordEnc(oldPassword);
if (!encOldPass.Equals(drUser.password))
{
return JsonConvert.SerializeObject(new { Success = false, Message = "기존 암호가 일치하지 않습니다." });
}
}
drUser.password = Pub.MakePasswordEnc(newPassword);
drUser.EndEdit();
taUser.Update(dtUser);
taUser.Dispose();
return JsonConvert.SerializeObject(new { Success = true, Message = "비밀번호가 변경되었습니다." });
}
catch (Exception ex)
{
return JsonConvert.SerializeObject(new { Success = false, Message = "비밀번호 변경 실패: " + ex.Message });
}
}
#endregion
}
/// <summary>
/// 사용자 정보 데이터 클래스
/// </summary>
public class UserInfoData
{
public string Id { get; set; }
public string NameK { get; set; }
public string NameE { get; set; }
public string Dept { get; set; }
public string Grade { get; set; }
public string Email { get; set; }
public string Tel { get; set; }
public string Hp { get; set; }
public string DateIn { get; set; }
public string DateO { get; set; }
public string Memo { get; set; }
public string Process { get; set; }
public string State { get; set; }
public bool UseJobReport { get; set; }
public bool UseUserState { get; set; }
public bool ExceptHoly { get; set; }
}
}