package progress import ( "cpone-dashboard/menu/auth" "cpone-dashboard/menu/projects" "html/template" "net/http" "strconv" ) var tmpl *template.Template var basePath string const defaultPageSize = 30 func SetTemplates(t *template.Template) { tmpl = t } func SetBasePath(p string) { basePath = p } type pageData struct { Username string CurrentProject projects.ProjectItem Search string Status string Rows []ProgressRow FilteredRows []ProgressRow Summary ProgressSummary ValidatedPct int PublishedPct int Page int PageSize int HasMore bool VisibleCount int TotalFiltered int NextPage int } func parsePage(q string) int { p, err := strconv.Atoi(q) if err != nil || p < 1 { return 1 } return p } func buildProgressData(r *http.Request) (pageData, int, error) { username := auth.Username(r) mcuID := auth.SelectedProjectID(r) if mcuID == 0 { return pageData{}, http.StatusSeeOther, nil } project, ok, err := projects.GetUserProject(username, mcuID) if err != nil { return pageData{}, http.StatusInternalServerError, err } if !ok { return pageData{}, http.StatusSeeOther, nil } rows, err := GetProgressRows(mcuID) if err != nil { return pageData{}, http.StatusInternalServerError, err } summary := BuildProgressSummary(rows) search := r.URL.Query().Get("search") status := r.URL.Query().Get("status") filteredRows := FilterProgressRows(rows, search, status) page := parsePage(r.URL.Query().Get("page")) pagedRows, hasMore := PaginateProgressRows(filteredRows, page, defaultPageSize) visibleCount := page * defaultPageSize if visibleCount > len(filteredRows) { visibleCount = len(filteredRows) } return pageData{ Username: username, CurrentProject: project, Search: search, Status: status, Rows: rows, FilteredRows: pagedRows, Summary: summary, ValidatedPct: Pct(summary.Validated, summary.Total), PublishedPct: Pct(summary.Published, summary.Total), Page: page, PageSize: defaultPageSize, HasMore: hasMore, VisibleCount: visibleCount, TotalFiltered: len(filteredRows), NextPage: page + 1, }, http.StatusOK, nil } func Index(w http.ResponseWriter, r *http.Request) { t := tmpl if t == nil { http.Error(w, "template not ready", http.StatusInternalServerError) return } data, status, err := buildProgressData(r) if err != nil { http.Error(w, "query error", status) return } if status == http.StatusSeeOther { http.Redirect(w, r, basePath+"/projects", http.StatusSeeOther) return } if err := t.ExecuteTemplate(w, "base", data); err != nil { http.Error(w, "template error", http.StatusInternalServerError) } } func List(w http.ResponseWriter, r *http.Request) { t := tmpl if t == nil { http.Error(w, "template not ready", http.StatusInternalServerError) return } data, status, err := buildProgressData(r) if err != nil { http.Error(w, "query error", status) return } if status == http.StatusSeeOther { http.Error(w, "unauthorized", http.StatusUnauthorized) return } if err := t.ExecuteTemplate(w, "progress-list-chunk", data); err != nil { http.Error(w, "template error", http.StatusInternalServerError) } }