-
Notifications
You must be signed in to change notification settings - Fork 576
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add convenience wrappers for http.Get/Post, etc. (#390)
* Add convenience wrappers for http.Get/Post, etc. Add convenience wrappers for http.{Get,Post,Head,PostForm} using the otelhttp transport and taking a context.Context directly. Makes instrumenting code using the original http convenience methods a one-line change instead of a multiline one. * Update instrumentation/net/http/otelhttp/client.go Co-authored-by: Anthony Mirabella <a9@aneurysm9.com> * Update instrumentation/net/http/otelhttp/client.go Co-authored-by: Anthony Mirabella <a9@aneurysm9.com> * Update instrumentation/net/http/otelhttp/client.go Co-authored-by: Anthony Mirabella <a9@aneurysm9.com> * Update instrumentation/net/http/otelhttp/client.go Co-authored-by: Anthony Mirabella <a9@aneurysm9.com> * Document new convenience wrappers in CHANGELOG * Add tests, don't use cached global client. * code format * Expose DefaultClient and use it for all convenience wrappers. * Update instrumentation/net/http/otelhttp/client.go Co-authored-by: Sam Xie <xsambundy@gmail.com> * Update CHANGELOG.md Co-authored-by: Tyler Yahn <MrAlias@users.noreply.github.com> * Don't bother attempting to reset the global provider. * Assert existence of 4 clients spans for 4 client operations * Improve comment on DefaultClient. * Improve span testing. * Move release note to unreleased section Co-authored-by: Anthony Mirabella <a9@aneurysm9.com> Co-authored-by: Sam Xie <xsambundy@gmail.com> Co-authored-by: Tyler Yahn <MrAlias@users.noreply.github.com>
- Loading branch information
1 parent
15f50e0
commit 4f3d787
Showing
3 changed files
with
145 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,61 @@ | ||
// Copyright The OpenTelemetry Authors | ||
// | ||
// Licensed under the Apache License, Version 2.0 (the "License"); | ||
// you may not use this file except in compliance with the License. | ||
// You may obtain a copy of the License at | ||
// | ||
// http://www.apache.org/licenses/LICENSE-2.0 | ||
// | ||
// Unless required by applicable law or agreed to in writing, software | ||
// distributed under the License is distributed on an "AS IS" BASIS, | ||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
// See the License for the specific language governing permissions and | ||
// limitations under the License. | ||
|
||
package otelhttp | ||
|
||
import ( | ||
"context" | ||
"io" | ||
"net/http" | ||
"net/url" | ||
"strings" | ||
) | ||
|
||
// DefaultClient is the default Client and is used by Get, Head, Post and PostForm. | ||
// Please be careful of intitialization order - for example, if you change | ||
// the global propagator, the DefaultClient might still be using the old one | ||
var DefaultClient = &http.Client{Transport: NewTransport(http.DefaultTransport)} | ||
|
||
// Get is a convenient replacement for http.Get that adds a span around the request. | ||
func Get(ctx context.Context, url string) (resp *http.Response, err error) { | ||
req, err := http.NewRequestWithContext(ctx, "GET", url, nil) | ||
if err != nil { | ||
return nil, err | ||
} | ||
return DefaultClient.Do(req) | ||
} | ||
|
||
// Head is a convenient replacement for http.Head that adds a span around the request. | ||
func Head(ctx context.Context, url string) (resp *http.Response, err error) { | ||
req, err := http.NewRequestWithContext(ctx, "HEAD", url, nil) | ||
if err != nil { | ||
return nil, err | ||
} | ||
return DefaultClient.Do(req) | ||
} | ||
|
||
// Post is a convenient replacement for http.Post that adds a span around the request. | ||
func Post(ctx context.Context, url, contentType string, body io.Reader) (resp *http.Response, err error) { | ||
req, err := http.NewRequestWithContext(ctx, "POST", url, body) | ||
if err != nil { | ||
return nil, err | ||
} | ||
req.Header.Set("Content-Type", contentType) | ||
return DefaultClient.Do(req) | ||
} | ||
|
||
// PostForm is a convenient replacement for http.PostForm that adds a span around the request. | ||
func PostForm(ctx context.Context, url string, data url.Values) (resp *http.Response, err error) { | ||
return Post(ctx, url, "application/x-www-form-urlencoded", strings.NewReader(data.Encode())) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,80 @@ | ||
// Copyright The OpenTelemetry Authors | ||
// | ||
// Licensed under the Apache License, Version 2.0 (the "License"); | ||
// you may not use this file except in compliance with the License. | ||
// You may obtain a copy of the License at | ||
// | ||
// http://www.apache.org/licenses/LICENSE-2.0 | ||
// | ||
// Unless required by applicable law or agreed to in writing, software | ||
// distributed under the License is distributed on an "AS IS" BASIS, | ||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
// See the License for the specific language governing permissions and | ||
// limitations under the License. | ||
|
||
package otelhttp | ||
|
||
import ( | ||
"context" | ||
"net/http" | ||
"net/http/httptest" | ||
"net/url" | ||
"strings" | ||
"testing" | ||
|
||
"go.opentelemetry.io/otel/api/global" | ||
|
||
"github.com/stretchr/testify/assert" | ||
|
||
mocktrace "go.opentelemetry.io/contrib/internal/trace" | ||
) | ||
|
||
func TestConvenienceWrappers(t *testing.T) { | ||
provider, tracer := mocktrace.NewTracerProviderAndTracer(instrumentationName) | ||
global.SetTracerProvider(provider) | ||
|
||
content := []byte("Hello, world!") | ||
|
||
ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { | ||
if _, err := w.Write(content); err != nil { | ||
t.Fatal(err) | ||
} | ||
})) | ||
defer ts.Close() | ||
|
||
context, span := tracer.Start(context.Background(), "parent") | ||
defer span.End() | ||
|
||
res, err := Get(context, ts.URL) | ||
if err != nil { | ||
t.Fatal(err) | ||
} | ||
res.Body.Close() | ||
|
||
res, err = Head(context, ts.URL) | ||
if err != nil { | ||
t.Fatal(err) | ||
} | ||
res.Body.Close() | ||
|
||
res, err = Post(context, ts.URL, "text/plain", strings.NewReader("test")) | ||
if err != nil { | ||
t.Fatal(err) | ||
} | ||
res.Body.Close() | ||
|
||
form := make(url.Values) | ||
form.Set("foo", "bar") | ||
res, err = PostForm(context, ts.URL, form) | ||
if err != nil { | ||
t.Fatal(err) | ||
} | ||
res.Body.Close() | ||
|
||
spans := tracer.EndedSpans() | ||
assert.Equal(t, 4, len(spans)) | ||
assert.Equal(t, "GET", spans[0].Name) | ||
assert.Equal(t, "HEAD", spans[1].Name) | ||
assert.Equal(t, "POST", spans[2].Name) | ||
assert.Equal(t, "POST", spans[3].Name) | ||
} |