package handlers import ( "encoding/json" "net/http" "xorm.io/xorm" "github.com/forgeo/forgebucket/internal/api/middleware" "github.com/forgeo/forgebucket/internal/models" ) type LFSHandler struct{ db *xorm.Engine } func NewLFSHandler(db *xorm.Engine) *LFSHandler { return &LFSHandler{db: db} } func (h *LFSHandler) resolveRepo(w http.ResponseWriter, r *http.Request) (*models.Repository, bool) { return resolveRepo(h.db, w, r) } func (h *LFSHandler) canManage(repo *models.Repository, callerID int64) bool { if callerID == repo.OwnerID { return true } var m models.RepoMember found, _ := h.db.Where("repo_id = ? AND user_id = ? AND permission = 'admin'", repo.ID, callerID).Get(&m) return found } func (h *LFSHandler) Get(w http.ResponseWriter, r *http.Request) { repo, ok := h.resolveRepo(w, r) if !ok { return } var s models.RepoLFSSettings h.db.Where("repo_id = ?", repo.ID).Get(&s) jsonOK(w, lfsResponse(repo.ID, &s)) } func (h *LFSHandler) Update(w http.ResponseWriter, r *http.Request) { repo, ok := h.resolveRepo(w, r) if !ok { return } callerID, _ := middleware.UserIDFromContext(r.Context()) if !h.canManage(repo, callerID) { jsonError(w, "forbidden", http.StatusForbidden) return } var body struct { Enabled *bool `json:"enabled"` LockingEnabled *bool `json:"lockingEnabled"` MaxFileSizeMB *int64 `json:"maxFileSizeMB"` } if err := json.NewDecoder(r.Body).Decode(&body); err != nil { jsonError(w, "invalid request body", http.StatusBadRequest) return } var s models.RepoLFSSettings found, err := h.db.Where("repo_id = ?", repo.ID).Get(&s) if err != nil { jsonError(w, "database error: "+err.Error(), http.StatusInternalServerError) return } s.RepoID = repo.ID if body.Enabled != nil { s.Enabled = *body.Enabled } if body.LockingEnabled != nil { s.LockingEnabled = *body.LockingEnabled } if body.MaxFileSizeMB != nil { s.MaxFileSizeMB = *body.MaxFileSizeMB } if found { if _, err := h.db.ID(s.ID).Cols("enabled", "locking_enabled", "max_file_size_mb").Update(&s); err != nil { jsonError(w, "could not update LFS settings", http.StatusInternalServerError) return } } else { if _, err := h.db.Insert(&s); err != nil { jsonError(w, "could not save LFS settings", http.StatusInternalServerError) return } } jsonOK(w, lfsResponse(repo.ID, &s)) } type lfsSettingsResponse struct { Enabled bool `json:"enabled"` LockingEnabled bool `json:"lockingEnabled"` MaxFileSizeMB int64 `json:"maxFileSizeMB"` } func lfsResponse(_ int64, s *models.RepoLFSSettings) lfsSettingsResponse { return lfsSettingsResponse{ Enabled: s.Enabled, LockingEnabled: s.LockingEnabled, MaxFileSizeMB: s.MaxFileSizeMB, } }