diff --git a/pkg/api/page_stats.go b/pkg/api/page_stats.go index e26d1b9..e315240 100644 --- a/pkg/api/page_stats.go +++ b/pkg/api/page_stats.go @@ -8,9 +8,8 @@ import ( // URL: /api/stats/page var GetPageStatsHandler = HandlerFunc(func(w http.ResponseWriter, r *http.Request) error { - startDate, endDate := getRequestedDatePeriods(r) - limit := getRequestedLimit(r) - result, err := datastore.GetAggregatedPageStats(startDate, endDate, limit) + params := GetRequestParams(r) + result, err := datastore.GetAggregatedPageStats(params.StartDate, params.EndDate, params.Limit) if err != nil { return err } diff --git a/pkg/api/params.go b/pkg/api/params.go index d94b69a..f2236e6 100644 --- a/pkg/api/params.go +++ b/pkg/api/params.go @@ -7,39 +7,33 @@ import ( "time" ) -// TODO: Move params into Params struct (with defaults) - -const defaultPeriod = 7 -const defaultLimit = 10 - -func getRequestedLimit(r *http.Request) int64 { - limit, err := strconv.ParseInt(r.URL.Query().Get("limit"), 10, 64) - if err != nil || limit == 0 { - limit = defaultLimit - } - - return limit +type Params struct { + Limit int + StartDate time.Time + EndDate time.Time } -func getRequestedDatePeriods(r *http.Request) (time.Time, time.Time) { - var startDate, endDate time.Time - var err error - - beforeUnix, err := strconv.ParseInt(r.URL.Query().Get("before"), 10, 64) - if err != nil || beforeUnix == 0 { - endDate = time.Now() - } else { - endDate = time.Unix(beforeUnix, 0) +func GetRequestParams(r *http.Request) *Params { + params := &Params{ + Limit: 20, + StartDate: time.Now(), + EndDate: time.Now().AddDate(0, 0, -7), } - afterUnix, err := strconv.ParseInt(r.URL.Query().Get("after"), 10, 64) - if err != nil || afterUnix == 0 { - startDate = endDate.AddDate(0, 0, -defaultPeriod) - } else { - startDate = time.Unix(afterUnix, 0) + q := r.URL.Query() + if after, err := strconv.ParseInt(q.Get("after"), 10, 64); err == nil && after > 0 { + params.StartDate = time.Unix(after, 0) } - return startDate, endDate + if before, err := strconv.ParseInt(q.Get("before"), 10, 64); err == nil && before > 0 { + params.EndDate = time.Unix(before, 0) + } + + if limit, err := strconv.Atoi(q.Get("limit")); err == nil && limit > 0 { + params.Limit = limit + } + + return params } func parseMajorMinor(v string) string { diff --git a/pkg/api/params_test.go b/pkg/api/params_test.go index a4d9ef0..6c34dfd 100644 --- a/pkg/api/params_test.go +++ b/pkg/api/params_test.go @@ -7,28 +7,8 @@ import ( "testing" ) -func TestGetRequestedLimit(t *testing.T) { - r, _ := http.NewRequest("GET", "", nil) - limit := getRequestedLimit(r) - - if limit != defaultLimit { - t.Errorf("Expected limit of %d does not match %d", defaultLimit, limit) - } - - r, _ = http.NewRequest("GET", "?limit=50", nil) - limit = getRequestedLimit(r) - if limit != 50 { - t.Errorf("Expected limit of %d does not match %d", defaultLimit, limit) - } -} - -func TestGetRequestedPeriods(t *testing.T) { - r, _ := http.NewRequest("GET", "?before=500&after=100", nil) - before, after := getRequestedPeriods(r) - - if before != 500 || after != 100 { - t.Error("Expected URl argument for `before` or `after` does not match") - } +func TestGetRequestParams(t *testing.T) { + // TODO: Implement this } func TestParseMajorMinor(t *testing.T) { diff --git a/pkg/api/site_stats.go b/pkg/api/site_stats.go index 23da44d..36daca5 100644 --- a/pkg/api/site_stats.go +++ b/pkg/api/site_stats.go @@ -18,8 +18,8 @@ var GetSiteStatsHandler = HandlerFunc(func(w http.ResponseWriter, r *http.Reques // URL: /api/stats/site/pageviews var GetSiteStatsPageviewsHandler = HandlerFunc(func(w http.ResponseWriter, r *http.Request) error { - startDate, endDate := getRequestedDatePeriods(r) - result, err := datastore.GetTotalSiteViews(startDate, endDate) + params := GetRequestParams(r) + result, err := datastore.GetTotalSiteViews(params.StartDate, params.EndDate) if err != nil { return err } @@ -28,8 +28,8 @@ var GetSiteStatsPageviewsHandler = HandlerFunc(func(w http.ResponseWriter, r *ht // URL: /api/stats/site/visitors var GetSiteStatsVisitorsHandler = HandlerFunc(func(w http.ResponseWriter, r *http.Request) error { - startDate, endDate := getRequestedDatePeriods(r) - result, err := datastore.GetTotalSiteVisitors(startDate, endDate) + params := GetRequestParams(r) + result, err := datastore.GetTotalSiteVisitors(params.StartDate, params.EndDate) if err != nil { return err } @@ -38,8 +38,8 @@ var GetSiteStatsVisitorsHandler = HandlerFunc(func(w http.ResponseWriter, r *htt // URL: /api/stats/site/duration var GetSiteStatsDurationHandler = HandlerFunc(func(w http.ResponseWriter, r *http.Request) error { - startDate, endDate := getRequestedDatePeriods(r) - result, err := datastore.GetAverageSiteDuration(startDate, endDate) + params := GetRequestParams(r) + result, err := datastore.GetAverageSiteDuration(params.StartDate, params.EndDate) if err != nil { return err } @@ -48,8 +48,8 @@ var GetSiteStatsDurationHandler = HandlerFunc(func(w http.ResponseWriter, r *htt // URL: /api/stats/site/bounces var GetSiteStatsBouncesHandler = HandlerFunc(func(w http.ResponseWriter, r *http.Request) error { - startDate, endDate := getRequestedDatePeriods(r) - result, err := datastore.GetAverageSiteBounceRate(startDate, endDate) + params := GetRequestParams(r) + result, err := datastore.GetAverageSiteBounceRate(params.StartDate, params.EndDate) if err != nil { return err } diff --git a/pkg/datastore/page_stats.go b/pkg/datastore/page_stats.go index 693d7b0..76b5f46 100644 --- a/pkg/datastore/page_stats.go +++ b/pkg/datastore/page_stats.go @@ -28,7 +28,7 @@ func UpdatePageStats(s *models.PageStats) error { return err } -func GetAggregatedPageStats(startDate time.Time, endDate time.Time, limit int64) ([]*models.PageStats, error) { +func GetAggregatedPageStats(startDate time.Time, endDate time.Time, limit int) ([]*models.PageStats, error) { var result []*models.PageStats query := dbx.Rebind(`SELECT pathname, SUM(views) AS views, SUM(unique_views) AS unique_views, SUM(entries) AS entries, ROUND(AVG(bounces), 0) AS bounces FROM daily_page_stats WHERE date >= ? AND date <= ? GROUP BY pathname, views, unique_views, entries, bounces ORDER BY views DESC LIMIT ?`) err := dbx.Select(&result, query, startDate.Format("2006-01-02"), endDate.Format("2006-01-02"), limit) diff --git a/pkg/datastore/site_stats.go b/pkg/datastore/site_stats.go index dedc090..4db8364 100644 --- a/pkg/datastore/site_stats.go +++ b/pkg/datastore/site_stats.go @@ -28,50 +28,50 @@ func UpdateSiteStats(s *models.SiteStats) error { return err } -func GetTotalSiteViews(startDate time.Time, endDate time.Time) (int64, error) { +func GetTotalSiteViews(startDate time.Time, endDate time.Time) (int, error) { sql := `SELECT COALESCE(SUM(pageviews), 0) FROM daily_site_stats WHERE date >= ? AND date <= ?` query := dbx.Rebind(sql) - var total int64 + var total int err := dbx.Get(&total, query, startDate.Format("2006-01-02"), endDate.Format("2006-01-02")) return total, err } -func GetTotalSiteVisitors(startDate time.Time, endDate time.Time) (int64, error) { +func GetTotalSiteVisitors(startDate time.Time, endDate time.Time) (int, error) { sql := `SELECT COALESCE(SUM(visitors), 0) FROM daily_site_stats WHERE date >= ? AND date <= ?` query := dbx.Rebind(sql) - var total int64 + var total int err := dbx.Get(&total, query, startDate.Format("2006-01-02"), endDate.Format("2006-01-02")) return total, err } -func GetTotalSiteSessions(startDate time.Time, endDate time.Time) (int64, error) { +func GetTotalSiteSessions(startDate time.Time, endDate time.Time) (int, error) { sql := `SELECT COALESCE(SUM(sessions), 0) FROM daily_site_stats WHERE date >= ? AND date <= ?` query := dbx.Rebind(sql) - var total int64 + var total int err := dbx.Get(&total, query, startDate.Format("2006-01-02"), endDate.Format("2006-01-02")) return total, err } -func GetAverageSiteDuration(startDate time.Time, endDate time.Time) (int64, error) { +func GetAverageSiteDuration(startDate time.Time, endDate time.Time) (int, error) { sql := `SELECT COALESCE(ROUND(AVG(avg_duration), 0), 0) FROM daily_site_stats WHERE date >= ? AND date <= ?` query := dbx.Rebind(sql) - var total int64 + var total int err := dbx.Get(&total, query, startDate.Format("2006-01-02"), endDate.Format("2006-01-02")) return total, err } -func GetAverageSiteBounceRate(startDate time.Time, endDate time.Time) (int64, error) { +func GetAverageSiteBounceRate(startDate time.Time, endDate time.Time) (int, error) { sql := `SELECT COALESCE(ROUND(AVG(bounces), 0), 0) FROM daily_site_stats WHERE date >= ? AND date <= ?` query := dbx.Rebind(sql) - var total int64 + var total int err := dbx.Get(&total, query, startDate.Format("2006-01-02"), endDate.Format("2006-01-02")) return total, err } -func GetRealtimeVisitorCount() (int64, error) { +func GetRealtimeVisitorCount() (int, error) { sql := `SELECT COUNT(DISTINCT(session_id)) FROM pageviews WHERE timestamp > ?` query := dbx.Rebind(sql) - var total int64 + var total int err := dbx.Get(&total, query, time.Now().Add(-5*time.Minute)) return total, err }