1
2
3
4
5
6
7
8
9
10
11
12
13
14 package test
15
16 import (
17 "context"
18 "net/http"
19 "net/http/httptest"
20 "net/url"
21 "testing"
22 "time"
23
24 "github.com/prometheus/common/model"
25 "github.com/stretchr/testify/require"
26
27 "github.com/prometheus/alertmanager/notify"
28 "github.com/prometheus/alertmanager/template"
29 "github.com/prometheus/alertmanager/types"
30 )
31
32
33 func RetryTests(retryCodes []int) map[int]bool {
34 tests := map[int]bool{
35
36 http.StatusContinue: false,
37 http.StatusSwitchingProtocols: false,
38 http.StatusProcessing: false,
39
40
41 http.StatusOK: false,
42 http.StatusCreated: false,
43 http.StatusAccepted: false,
44 http.StatusNonAuthoritativeInfo: false,
45 http.StatusNoContent: false,
46 http.StatusResetContent: false,
47 http.StatusPartialContent: false,
48 http.StatusMultiStatus: false,
49 http.StatusAlreadyReported: false,
50 http.StatusIMUsed: false,
51
52
53 http.StatusMultipleChoices: false,
54 http.StatusMovedPermanently: false,
55 http.StatusFound: false,
56 http.StatusSeeOther: false,
57 http.StatusNotModified: false,
58 http.StatusUseProxy: false,
59 http.StatusTemporaryRedirect: false,
60 http.StatusPermanentRedirect: false,
61
62
63 http.StatusBadRequest: false,
64 http.StatusUnauthorized: false,
65 http.StatusPaymentRequired: false,
66 http.StatusForbidden: false,
67 http.StatusNotFound: false,
68 http.StatusMethodNotAllowed: false,
69 http.StatusNotAcceptable: false,
70 http.StatusProxyAuthRequired: false,
71 http.StatusRequestTimeout: false,
72 http.StatusConflict: false,
73 http.StatusGone: false,
74 http.StatusLengthRequired: false,
75 http.StatusPreconditionFailed: false,
76 http.StatusRequestEntityTooLarge: false,
77 http.StatusRequestURITooLong: false,
78 http.StatusUnsupportedMediaType: false,
79 http.StatusRequestedRangeNotSatisfiable: false,
80 http.StatusExpectationFailed: false,
81 http.StatusTeapot: false,
82 http.StatusUnprocessableEntity: false,
83 http.StatusLocked: false,
84 http.StatusFailedDependency: false,
85 http.StatusUpgradeRequired: false,
86 http.StatusPreconditionRequired: false,
87 http.StatusTooManyRequests: false,
88 http.StatusRequestHeaderFieldsTooLarge: false,
89 http.StatusUnavailableForLegalReasons: false,
90
91
92 http.StatusInternalServerError: false,
93 http.StatusNotImplemented: false,
94 http.StatusBadGateway: false,
95 http.StatusServiceUnavailable: false,
96 http.StatusGatewayTimeout: false,
97 http.StatusHTTPVersionNotSupported: false,
98 http.StatusVariantAlsoNegotiates: false,
99 http.StatusInsufficientStorage: false,
100 http.StatusLoopDetected: false,
101 http.StatusNotExtended: false,
102 http.StatusNetworkAuthenticationRequired: false,
103 }
104
105 for _, statusCode := range retryCodes {
106 tests[statusCode] = true
107 }
108
109 return tests
110 }
111
112
113 func DefaultRetryCodes() []int {
114 return []int{
115 http.StatusInternalServerError,
116 http.StatusNotImplemented,
117 http.StatusBadGateway,
118 http.StatusServiceUnavailable,
119 http.StatusGatewayTimeout,
120 http.StatusHTTPVersionNotSupported,
121 http.StatusVariantAlsoNegotiates,
122 http.StatusInsufficientStorage,
123 http.StatusLoopDetected,
124 http.StatusNotExtended,
125 http.StatusNetworkAuthenticationRequired,
126 }
127 }
128
129
130 func CreateTmpl(t *testing.T) *template.Template {
131 tmpl, err := template.FromGlobs()
132 require.NoError(t, err)
133 tmpl.ExternalURL, _ = url.Parse("http://am")
134 return tmpl
135 }
136
137
138
139
140 func AssertNotifyLeaksNoSecret(ctx context.Context, t *testing.T, n notify.Notifier, secret ...string) {
141 t.Helper()
142 require.NotEmpty(t, secret)
143
144 ctx = notify.WithGroupKey(ctx, "1")
145 ok, err := n.Notify(ctx, []*types.Alert{
146 {
147 Alert: model.Alert{
148 Labels: model.LabelSet{
149 "lbl1": "val1",
150 },
151 StartsAt: time.Now(),
152 EndsAt: time.Now().Add(time.Hour),
153 },
154 },
155 }...)
156
157 require.Error(t, err)
158 require.Contains(t, err.Error(), context.Canceled.Error())
159 for _, s := range secret {
160 require.NotContains(t, err.Error(), s)
161 }
162 require.True(t, ok)
163 }
164
165
166
167
168
169 func GetContextWithCancelingURL(h ...func(w http.ResponseWriter, r *http.Request)) (context.Context, *url.URL, func()) {
170 done := make(chan struct{})
171 ctx, cancel := context.WithCancel(context.Background())
172 i := 0
173
174 srv := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
175 if i < len(h) {
176 h[i](w, r)
177 } else {
178 cancel()
179 <-done
180 }
181 i++
182 }))
183
184
185 u, _ := url.Parse(srv.URL)
186
187 return ctx, u, func() {
188 close(done)
189 srv.Close()
190 }
191 }
192
View as plain text