Skip to content

Commit

Permalink
Merge pull request #192 from rogpeppe/143-agent-environment
Browse files Browse the repository at this point in the history
httpbakery/agent: support authinfo in environment variables
  • Loading branch information
rogpeppe authored Apr 23, 2018
2 parents 3013033 + 55709bb commit a0743b6
Show file tree
Hide file tree
Showing 2 changed files with 73 additions and 0 deletions.
32 changes: 32 additions & 0 deletions httpbakery/agent/agent.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,11 @@
package agent

import (
"encoding/json"
"errors"
"io/ioutil"
"net/url"
"os"
"strings"

"golang.org/x/net/context"
Expand Down Expand Up @@ -37,6 +40,35 @@ type Agent struct {
Username string `json:"username" yaml:"username"`
}

var ErrNoAuthInfo = errgo.New("no bakery agent info found in environment")

// AuthInfoFromEnvironment returns an AuthInfo derived
// from environment variables.
//
// It recognizes the following variable:
// BAKERY_AGENT_FILE - path to a file containing agent authentication
// info in JSON format (as marshaled by the AuthInfo type).
//
// If BAKERY_AGENT_FILE is not set, ErrNoAuthInfo will be returned.
func AuthInfoFromEnvironment() (*AuthInfo, error) {
agentFile := os.Getenv("BAKERY_AGENT_FILE")
if agentFile == "" {
return nil, errgo.WithCausef(nil, ErrNoAuthInfo, "")
}
var ai AuthInfo
data, err := ioutil.ReadFile(agentFile)
if err != nil {
return nil, errgo.Mask(err)
}
if err := json.Unmarshal(data, &ai); err != nil {
return nil, errgo.Notef(err, "cannot unmarshal agent information from %q: %v", agentFile)
}
if ai.Key == nil {
return nil, errgo.Newf("no private key found in %q", agentFile)
}
return &ai, nil
}

// SetUpAuth sets up agent authentication on the given client.
// If this is called several times on the same client, earlier
// calls will take precedence over later calls when there's
Expand Down
41 changes: 41 additions & 0 deletions httpbakery/agent/agent_test.go
Original file line number Diff line number Diff line change
@@ -1,9 +1,13 @@
package agent_test

import (
"encoding/json"
"io/ioutil"
"net/http"
"os"

"github.com/juju/testing"
jc "github.com/juju/testing/checkers"
"golang.org/x/net/context"
gc "gopkg.in/check.v1"
"gopkg.in/errgo.v1"
Expand Down Expand Up @@ -117,6 +121,43 @@ func (s *agentSuite) TestSetUpAuth(c *gc.C) {
c.Assert(err, gc.Equals, nil)
}

func (s *agentSuite) TestAuthInfoFromEnvironment(c *gc.C) {
defer os.Setenv("BAKERY_AGENT_FILE", "")

f, err := ioutil.TempFile("", "")
c.Assert(err, gc.Equals, nil)
defer os.Remove(f.Name())
defer f.Close()

authInfo := &agent.AuthInfo{
Key: bakery.MustGenerateKey(),
Agents: []agent.Agent{{
URL: "https://0.1.2.3/x",
Username: "bob",
}, {
URL: "https://0.2.3.4",
Username: "charlie",
}},
}
data, err := json.Marshal(authInfo)
_, err = f.Write(data)
c.Assert(err, gc.Equals, nil)
f.Close()

os.Setenv("BAKERY_AGENT_FILE", f.Name())

authInfo1, err := agent.AuthInfoFromEnvironment()
c.Assert(err, gc.Equals, nil)
c.Assert(authInfo1, jc.DeepEquals, authInfo)
}

func (s *agentSuite) TestAuthInfoFromEnvironmentNotSet(c *gc.C) {
os.Setenv("BAKERY_AGENT_FILE", "")
authInfo, err := agent.AuthInfoFromEnvironment()
c.Assert(errgo.Cause(err), gc.Equals, agent.ErrNoAuthInfo)
c.Assert(authInfo, gc.IsNil)
}

func AgentHandlers(h AgentHandler) []httprequest.Handler {
return reqServer.Handlers(func(p httprequest.Params) (agentHandlers, context.Context, error) {
return agentHandlers{h}, p.Context, nil
Expand Down

0 comments on commit a0743b6

Please sign in to comment.