1
0
forked from baron/baron-sso

개발자 신청 API 단일화 및 RP 권한 자동 부여 구현

This commit is contained in:
2026-04-22 13:07:02 +09:00
parent 4dc274a5d7
commit 2216d9c4e4
9 changed files with 573 additions and 115 deletions

View File

@@ -15,6 +15,7 @@ import (
"log/slog"
"net/http"
"os"
"strconv"
"strings"
"time"
@@ -2865,3 +2866,105 @@ func (h *DevHandler) GetDeveloperRequestStatus(c *fiber.Ctx) error {
return c.JSON(status)
}
func (h *DevHandler) ListDeveloperRequests(c *fiber.Ctx) error {
profile := h.getCurrentProfile(c)
if profile == nil {
return errorJSON(c, fiber.StatusUnauthorized, "unauthorized")
}
role := normalizeUserRole(profile.Role)
status := c.Query("status")
userID := profile.ID
if role == domain.RoleSuperAdmin {
// Super Admin can see everyone's requests
userID = ""
}
requests, err := h.DeveloperSvc.ListRequests(c.Context(), userID, status)
if err != nil {
return errorJSON(c, fiber.StatusInternalServerError, err.Error())
}
return c.JSON(requests)
}
func (h *DevHandler) ApproveDeveloperRequest(c *fiber.Ctx) error {
profile := h.getCurrentProfile(c)
if profile == nil {
return errorJSON(c, fiber.StatusUnauthorized, "unauthorized")
}
if normalizeUserRole(profile.Role) != domain.RoleSuperAdmin {
return errorJSON(c, fiber.StatusForbidden, "forbidden: super_admin only")
}
idStr := c.Params("id")
id, err := strconv.ParseUint(idStr, 10, 32)
if err != nil {
return errorJSON(c, fiber.StatusBadRequest, "invalid request id")
}
var reqBody struct {
AdminNotes string `json:"adminNotes"`
}
if err := c.BodyParser(&reqBody); err != nil {
return errorJSON(c, fiber.StatusBadRequest, "invalid request body")
}
devReq, err := h.DeveloperSvc.GetRequestByID(c.Context(), uint(id))
if err != nil {
return errorJSON(c, fiber.StatusInternalServerError, "failed to fetch request details")
}
if err := h.DeveloperSvc.ApproveRequest(c.Context(), uint(id), reqBody.AdminNotes); err != nil {
return errorJSON(c, fiber.StatusInternalServerError, err.Error())
}
// Grant Keto Permissions
if h.KetoOutbox != nil {
subject := "User:" + devReq.UserID
permissions := []string{"view_dev_console", "grant_dev_permissions"}
for _, relation := range permissions {
_ = h.KetoOutbox.Create(c.Context(), &domain.KetoOutbox{
Namespace: "Tenant",
Object: devReq.TenantID,
Relation: relation,
Subject: subject,
Action: domain.KetoOutboxActionCreate,
})
}
}
return c.JSON(fiber.Map{"status": "ok"})
}
func (h *DevHandler) RejectDeveloperRequest(c *fiber.Ctx) error {
profile := h.getCurrentProfile(c)
if profile == nil {
return errorJSON(c, fiber.StatusUnauthorized, "unauthorized")
}
if normalizeUserRole(profile.Role) != domain.RoleSuperAdmin {
return errorJSON(c, fiber.StatusForbidden, "forbidden: super_admin only")
}
idStr := c.Params("id")
id, err := strconv.ParseUint(idStr, 10, 32)
if err != nil {
return errorJSON(c, fiber.StatusBadRequest, "invalid request id")
}
var reqBody struct {
AdminNotes string `json:"adminNotes"`
}
if err := c.BodyParser(&reqBody); err != nil {
return errorJSON(c, fiber.StatusBadRequest, "invalid request body")
}
if err := h.DeveloperSvc.RejectRequest(c.Context(), uint(id), reqBody.AdminNotes); err != nil {
return errorJSON(c, fiber.StatusInternalServerError, err.Error())
}
return c.JSON(fiber.Map{"status": "ok"})
}