-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathrolldice.go
More file actions
89 lines (74 loc) · 2.17 KB
/
rolldice.go
File metadata and controls
89 lines (74 loc) · 2.17 KB
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
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
package main
import (
"context"
"io"
"log"
"math/rand"
"net/http"
"strconv"
"time"
"go.opentelemetry.io/otel"
"go.opentelemetry.io/otel/attribute"
"go.opentelemetry.io/otel/metric"
)
var (
tracer = otel.Tracer("rolldice")
meter = otel.Meter("rolldice")
rollCnt metric.Int64Counter
)
func init() {
var err error
rollCnt, err = meter.Int64Counter("dice.rolls",
metric.WithDescription("The number of rolls by roll value"),
metric.WithUnit("{roll}"))
if err != nil {
panic(err)
}
}
func rolldice(w http.ResponseWriter, r *http.Request) {
ctx, span := tracer.Start(r.Context(), "rolling dice")
defer span.End()
roll := 1 + rand.Intn(6)
// Sleep for a few seconds, so we can see longer traces
// And breakout the slow api call versus other work
// that might be done in this function, i.e. a DB query
time.Sleep(time.Millisecond * time.Duration(roll*100))
span.AddEvent("simulating a call to slow api")
err := simulateSlowAPI(500*roll, ctx)
if err != nil {
log.Printf("Failed to make call to simulate slow api")
}
rollValueAttr := attribute.Int("roll.value", roll)
span.SetAttributes(rollValueAttr)
rollCnt.Add(ctx, 1, metric.WithAttributes(rollValueAttr))
resp := strconv.Itoa(roll) + "\n"
if _, err := io.WriteString(w, resp); err != nil {
log.Printf("Write failed: %v\n", err)
}
}
// A function for simulating slowness with an external http call
func simulateSlowAPI(sleepInMilliseconds int, ctx context.Context) error {
ctx, childSpan := tracer.Start(ctx, "simulatedSlowApiSpan")
defer childSpan.End()
// Construct the URL with the sleep parameter
baseURL := "https://fakeresponder.com/"
sleepParam := "?sleep=" + strconv.Itoa(sleepInMilliseconds)
// Create the full URL
fullURL := baseURL + sleepParam
// Make the GET request
childSpan.AddEvent("GET fakeresponder.com api")
resp, err := http.Get(fullURL)
if err != nil {
log.Println("Error making the GET request:", err)
return err
}
defer resp.Body.Close()
// We can ignore the response body
// But if you want to see it, uncomment this
// body, err := io.ReadAll(resp.Body)
// if err != nil {
// log.Println("Error reading the response body:", err)
// return err
// }
return nil
}