How to use go-vcr with githubv4 ? – getting httpClient Transport

Issue

Looking at the set up for go-vcr

// Start our recorder
    r, err := recorder.New("fixtures/etcd")
    if err != nil {
        log.Fatal(err)
    }
    defer r.Stop() // Make sure recorder is stopped once done with it

    // Create an etcd configuration using our transport
    cfg := client.Config{
        Endpoints:               []string{"http://127.0.0.1:2379"},
        HeaderTimeoutPerRequest: time.Second,
        Transport:               r, // Inject as transport!
    }

Attempting to use this library using the githubv4 library seems at though it needs a way to handle Oauth

import "golang.org/x/oauth2"

func main() {
    src := oauth2.StaticTokenSource(
        &oauth2.Token{AccessToken: os.Getenv("GITHUB_TOKEN")},
    )
    httpClient := oauth2.NewClient(context.Background(), src)

    client := githubv4.NewClient(httpClient)
    // Use client...
}

I’m not sure how to get the recorder ‘r’ into the oauth2 client. If at all possible.

Has anyone been successful with this? I’ve tried passing in a httpClient with the ‘r’ recorder but it ends up as a 401 – looks like this default client can’t do the Oauth dance.

I’d like to use the GraphQL API but can fall back to the REST API if is is easier but I just want to make sure this isn’t really possible. Has anyone else been successful with this?

Solution

This issue resolved this question for me.
https://github.com/dnaeon/go-vcr/issues/59

Example below

package example_test

import (
    "context"
    "github.com/dnaeon/go-vcr/cassette"
    "github.com/dnaeon/go-vcr/recorder"
    "github.com/google/go-github/v33/github"
    "github.com/stretchr/testify/require"
    "golang.org/x/oauth2"
    "net/http"
    "path"
    "testing"
)

func TestGithub(t *testing.T) {
    //custom http.Transport, since github uses oauth2 authentication
    ts := oauth2.StaticTokenSource(
        &oauth2.Token{AccessToken: "YOUR_GITHUB_TOKEN"},
    )

    tr := &oauth2.Transport{
        Base:  http.DefaultTransport,
        Source: oauth2.ReuseTokenSource(nil, ts),
    }

    // Start our recorder
    vcrRecorder, err := recorder.NewAsMode(path.Join("testdata", "fixtures", t.Name()), recorder.ModeRecording, tr)
    require.NoError(t, err)
        defer vcrRecorder.Stop() // NEWLY ADDED CODE HERE


    // Filter out dynamic & sensitive data/headers
    // Your test code will continue to see the real access token and
    // it is redacted before the recorded interactions are saved
        // =====> commenting out this section has no impact on missing recording
    vcrRecorder.AddSaveFilter(func(i *cassette.Interaction) error {
        delete(i.Request.Headers, "Authorization")
        delete(i.Request.Headers, "User-Agent")
        i.Request.Headers["Authorization"] = []string{"Basic UExBQ0VIT0xERVI6UExBQ0VIT0xERVI="} //PLACEHOLDER:PLACEHOLDER

        return nil
    })

        // custom http.client
    httpClient := &http.Client{
        Transport: vcrRecorder,
    }

    ghClient := github.NewClient(httpClient)

    // =====> actual test, should create cassettes, but does not.
    _, _, err = ghClient.Users.Get(context.Background(), "")

    require.NoError(t, err)
}

Answered By – mcbain83

Answer Checked By – Gilberto Lyons (GoLangFix Admin)

Leave a Reply

Your email address will not be published.