-
Notifications
You must be signed in to change notification settings - Fork 19
/
Copy pathstats.go
58 lines (52 loc) · 1.29 KB
/
stats.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
package main
import (
"context"
"github.com/jmoiron/sqlx"
"github.com/pkg/errors"
)
type Stats struct {
Products int `json:"products"`
Customers int `json:"customers"`
Orders int `json:"orders"`
Numbers struct {
Revenue int `json:"revenue"`
Cost int `json:"cost"`
Profit int `json:"profit"`
} `json:"numbers"`
}
func getStats(ctx context.Context, db *sqlx.DB) (*Stats, error) {
var stats Stats
countParams := []struct {
table string
result *int
}{
{"products", &stats.Products},
{"customers", &stats.Customers},
{"orders", &stats.Orders},
}
for _, p := range countParams {
row := db.QueryRowContext(ctx, `SELECT COUNT(*) FROM `+p.table)
if err := row.Scan(p.result); err != nil {
return nil, errors.Wrap(err, "querying "+p.table)
}
}
var revenue, cost, profit *int
row := db.QueryRowContext(ctx, `
SELECT
SUM(selling_price), SUM(cost), SUM(selling_price-cost)
FROM products JOIN order_lines ON products.id=order_lines.product_id
`)
if err := row.Scan(&revenue, &cost, &profit); err != nil {
return nil, errors.Wrap(err, "querying numbers")
}
stats.Numbers.Revenue = maybeInt(revenue)
stats.Numbers.Cost = maybeInt(cost)
stats.Numbers.Profit = maybeInt(profit)
return &stats, nil
}
func maybeInt(p *int) int {
if p == nil {
return 0
}
return *p
}