浏览代码

Move 'auth' to the registry subsystem

This is the first step towards separating the registry subsystem from
the deprecated `Server` object.

* New service `github.com/dotcloud/docker/registry/Service`
* The service is installed by default in `builtins`
* The service only exposes `auth` for now...
* ...Soon to be followed by `pull`, `push` and `search`.

Docker-DCO-1.1-Signed-off-by: Solomon Hykes <solomon@docker.com> (github: shykes)
Solomon Hykes 11 年之前
父节点
当前提交
3d605683b3
共有 4 个文件被更改,包括 100 次插入63 次删除
  1. 4 0
      builtins/builtins.go
  2. 39 0
      registry/registry.go
  3. 54 0
      registry/service.go
  4. 3 63
      server/server.go

+ 4 - 0
builtins/builtins.go

@@ -4,12 +4,16 @@ import (
 	api "github.com/dotcloud/docker/api/server"
 	"github.com/dotcloud/docker/daemon/networkdriver/bridge"
 	"github.com/dotcloud/docker/engine"
+	"github.com/dotcloud/docker/registry"
 	"github.com/dotcloud/docker/server"
 )
 
 func Register(eng *engine.Engine) {
 	daemon(eng)
 	remote(eng)
+	// FIXME: engine.Installer.Install can fail. These errors
+	// should be passed up.
+	registry.NewService().Install(eng)
 }
 
 // remote: a RESTful api for cross-docker communication

+ 39 - 0
registry/registry.go

@@ -13,10 +13,12 @@ import (
 	"net/http/cookiejar"
 	"net/url"
 	"regexp"
+	"runtime"
 	"strconv"
 	"strings"
 	"time"
 
+	"github.com/dotcloud/docker/dockerversion"
 	"github.com/dotcloud/docker/utils"
 )
 
@@ -757,3 +759,40 @@ func NewRegistry(authConfig *AuthConfig, factory *utils.HTTPRequestFactory, inde
 	r.reqFactory = factory
 	return r, nil
 }
+
+func HTTPRequestFactory(metaHeaders map[string][]string) *utils.HTTPRequestFactory {
+	// FIXME: this replicates the 'info' job.
+	httpVersion := make([]utils.VersionInfo, 0, 4)
+	httpVersion = append(httpVersion, &simpleVersionInfo{"docker", dockerversion.VERSION})
+	httpVersion = append(httpVersion, &simpleVersionInfo{"go", runtime.Version()})
+	httpVersion = append(httpVersion, &simpleVersionInfo{"git-commit", dockerversion.GITCOMMIT})
+	if kernelVersion, err := utils.GetKernelVersion(); err == nil {
+		httpVersion = append(httpVersion, &simpleVersionInfo{"kernel", kernelVersion.String()})
+	}
+	httpVersion = append(httpVersion, &simpleVersionInfo{"os", runtime.GOOS})
+	httpVersion = append(httpVersion, &simpleVersionInfo{"arch", runtime.GOARCH})
+	ud := utils.NewHTTPUserAgentDecorator(httpVersion...)
+	md := &utils.HTTPMetaHeadersDecorator{
+		Headers: metaHeaders,
+	}
+	factory := utils.NewHTTPRequestFactory(ud, md)
+	return factory
+}
+
+// simpleVersionInfo is a simple implementation of
+// the interface VersionInfo, which is used
+// to provide version information for some product,
+// component, etc. It stores the product name and the version
+// in string and returns them on calls to Name() and Version().
+type simpleVersionInfo struct {
+	name    string
+	version string
+}
+
+func (v *simpleVersionInfo) Name() string {
+	return v.name
+}
+
+func (v *simpleVersionInfo) Version() string {
+	return v.version
+}

+ 54 - 0
registry/service.go

@@ -0,0 +1,54 @@
+package registry
+
+import (
+	"github.com/dotcloud/docker/engine"
+)
+
+// Service exposes registry capabilities in the standard Engine
+// interface. Once installed, it extends the engine with the
+// following calls:
+//
+//  'auth': Authenticate against the public registry
+//  'search': Search for images on the public registry (TODO)
+//  'pull': Download images from any registry (TODO)
+//  'push': Upload images to any registry (TODO)
+type Service struct {
+}
+
+// NewService returns a new instance of Service ready to be
+// installed no an engine.
+func NewService() *Service {
+	return &Service{}
+}
+
+// Install installs registry capabilities to eng.
+func (s *Service) Install(eng *engine.Engine) error {
+	eng.Register("auth", s.Auth)
+	return nil
+}
+
+// Auth contacts the public registry with the provided credentials,
+// and returns OK if authentication was sucessful.
+// It can be used to verify the validity of a client's credentials.
+func (s *Service) Auth(job *engine.Job) engine.Status {
+	var (
+		err        error
+		authConfig = &AuthConfig{}
+	)
+
+	job.GetenvJson("authConfig", authConfig)
+	// TODO: this is only done here because auth and registry need to be merged into one pkg
+	if addr := authConfig.ServerAddress; addr != "" && addr != IndexServerAddress() {
+		addr, err = ExpandAndVerifyRegistryUrl(addr)
+		if err != nil {
+			return job.Error(err)
+		}
+		authConfig.ServerAddress = addr
+	}
+	status, err := Login(authConfig, HTTPRequestFactory(nil))
+	if err != nil {
+		return job.Error(err)
+	}
+	job.Printf("%s\n", status)
+	return engine.StatusOK
+}

+ 3 - 63
server/server.go

@@ -139,7 +139,6 @@ func InitServer(job *engine.Job) engine.Status {
 		"events":           srv.Events,
 		"push":             srv.ImagePush,
 		"containers":       srv.Containers,
-		"auth":             srv.Auth,
 	} {
 		if err := job.Eng.Register(name, handler); err != nil {
 			return job.Error(err)
@@ -148,24 +147,6 @@ func InitServer(job *engine.Job) engine.Status {
 	return engine.StatusOK
 }
 
-// simpleVersionInfo is a simple implementation of
-// the interface VersionInfo, which is used
-// to provide version information for some product,
-// component, etc. It stores the product name and the version
-// in string and returns them on calls to Name() and Version().
-type simpleVersionInfo struct {
-	name    string
-	version string
-}
-
-func (v *simpleVersionInfo) Name() string {
-	return v.name
-}
-
-func (v *simpleVersionInfo) Version() string {
-	return v.version
-}
-
 // ContainerKill send signal to the container
 // If no signal is given (sig 0), then Kill with SIGKILL and wait
 // for the container to exit.
@@ -215,29 +196,6 @@ func (srv *Server) ContainerKill(job *engine.Job) engine.Status {
 	return engine.StatusOK
 }
 
-func (srv *Server) Auth(job *engine.Job) engine.Status {
-	var (
-		err        error
-		authConfig = &registry.AuthConfig{}
-	)
-
-	job.GetenvJson("authConfig", authConfig)
-	// TODO: this is only done here because auth and registry need to be merged into one pkg
-	if addr := authConfig.ServerAddress; addr != "" && addr != registry.IndexServerAddress() {
-		addr, err = registry.ExpandAndVerifyRegistryUrl(addr)
-		if err != nil {
-			return job.Error(err)
-		}
-		authConfig.ServerAddress = addr
-	}
-	status, err := registry.Login(authConfig, srv.HTTPRequestFactory(nil))
-	if err != nil {
-		return job.Error(err)
-	}
-	job.Printf("%s\n", status)
-	return engine.StatusOK
-}
-
 func (srv *Server) Events(job *engine.Job) engine.Status {
 	if len(job.Args) != 1 {
 		return job.Errorf("Usage: %s FROM", job.Name)
@@ -654,7 +612,7 @@ func (srv *Server) ImagesSearch(job *engine.Job) engine.Status {
 	job.GetenvJson("authConfig", authConfig)
 	job.GetenvJson("metaHeaders", metaHeaders)
 
-	r, err := registry.NewRegistry(authConfig, srv.HTTPRequestFactory(metaHeaders), registry.IndexServerAddress())
+	r, err := registry.NewRegistry(authConfig, registry.HTTPRequestFactory(metaHeaders), registry.IndexServerAddress())
 	if err != nil {
 		return job.Error(err)
 	}
@@ -1457,7 +1415,7 @@ func (srv *Server) ImagePull(job *engine.Job) engine.Status {
 		return job.Error(err)
 	}
 
-	r, err := registry.NewRegistry(&authConfig, srv.HTTPRequestFactory(metaHeaders), endpoint)
+	r, err := registry.NewRegistry(&authConfig, registry.HTTPRequestFactory(metaHeaders), endpoint)
 	if err != nil {
 		return job.Error(err)
 	}
@@ -1680,7 +1638,7 @@ func (srv *Server) ImagePush(job *engine.Job) engine.Status {
 	}
 
 	img, err := srv.daemon.Graph().Get(localName)
-	r, err2 := registry.NewRegistry(authConfig, srv.HTTPRequestFactory(metaHeaders), endpoint)
+	r, err2 := registry.NewRegistry(authConfig, registry.HTTPRequestFactory(metaHeaders), endpoint)
 	if err2 != nil {
 		return job.Error(err2)
 	}
@@ -2558,24 +2516,6 @@ func NewServer(eng *engine.Engine, config *daemonconfig.Config) (*Server, error)
 	return srv, nil
 }
 
-func (srv *Server) HTTPRequestFactory(metaHeaders map[string][]string) *utils.HTTPRequestFactory {
-	httpVersion := make([]utils.VersionInfo, 0, 4)
-	httpVersion = append(httpVersion, &simpleVersionInfo{"docker", dockerversion.VERSION})
-	httpVersion = append(httpVersion, &simpleVersionInfo{"go", goruntime.Version()})
-	httpVersion = append(httpVersion, &simpleVersionInfo{"git-commit", dockerversion.GITCOMMIT})
-	if kernelVersion, err := utils.GetKernelVersion(); err == nil {
-		httpVersion = append(httpVersion, &simpleVersionInfo{"kernel", kernelVersion.String()})
-	}
-	httpVersion = append(httpVersion, &simpleVersionInfo{"os", goruntime.GOOS})
-	httpVersion = append(httpVersion, &simpleVersionInfo{"arch", goruntime.GOARCH})
-	ud := utils.NewHTTPUserAgentDecorator(httpVersion...)
-	md := &utils.HTTPMetaHeadersDecorator{
-		Headers: metaHeaders,
-	}
-	factory := utils.NewHTTPRequestFactory(ud, md)
-	return factory
-}
-
 func (srv *Server) LogEvent(action, id, from string) *utils.JSONMessage {
 	now := time.Now().UTC().Unix()
 	jm := utils.JSONMessage{Status: action, ID: id, From: from, Time: now}