From 68cad8e46b758e04f3b32107f11bda16f66da947 Mon Sep 17 00:00:00 2001 From: Tonis Tiigi Date: Wed, 10 Apr 2019 17:42:04 -0700 Subject: [PATCH] driver: add docker driver Signed-off-by: Tonis Tiigi --- cmd/buildx/main.go | 1 + driver/docker-container/factory.go | 14 +++++--- driver/docker/driver.go | 48 +++++++++++++++++++++++++++ driver/docker/factory.go | 53 ++++++++++++++++++++++++++++++ driver/manager.go | 17 +++++----- 5 files changed, 121 insertions(+), 12 deletions(-) create mode 100644 driver/docker/driver.go create mode 100644 driver/docker/factory.go diff --git a/cmd/buildx/main.go b/cmd/buildx/main.go index 312ead84..1c604558 100644 --- a/cmd/buildx/main.go +++ b/cmd/buildx/main.go @@ -8,6 +8,7 @@ import ( "github.com/tonistiigi/buildx/commands" "github.com/tonistiigi/buildx/version" + _ "github.com/tonistiigi/buildx/driver/docker" _ "github.com/tonistiigi/buildx/driver/docker-container" ) diff --git a/driver/docker-container/factory.go b/driver/docker-container/factory.go index 25980357..752d14a3 100644 --- a/driver/docker-container/factory.go +++ b/driver/docker-container/factory.go @@ -7,6 +7,9 @@ import ( "github.com/tonistiigi/buildx/driver" ) +const prioritySupported = 30 +const priorityUnsupported = 70 + func init() { driver.Register(&factory{}) } @@ -22,13 +25,16 @@ func (*factory) Usage() string { return "docker-container" } -func (*factory) Priority() int { - return 30 +func (*factory) Priority(cfg driver.InitConfig) int { + if cfg.DockerAPI == nil { + return priorityUnsupported + } + return prioritySupported } -func (*factory) New(ctx context.Context, cfg driver.InitConfig) (driver.Driver, error) { +func (f *factory) New(ctx context.Context, cfg driver.InitConfig) (driver.Driver, error) { if cfg.DockerAPI == nil { - return nil, errors.Errorf("docker driver requires docker API access") + return nil, errors.Errorf("%s driver requires docker API access", f.Name()) } v, err := cfg.DockerAPI.ServerVersion(ctx) diff --git a/driver/docker/driver.go b/driver/docker/driver.go new file mode 100644 index 00000000..75a1ac0d --- /dev/null +++ b/driver/docker/driver.go @@ -0,0 +1,48 @@ +package docker + +import ( + "context" + "net" + "time" + + dockertypes "github.com/docker/docker/api/types" + "github.com/moby/buildkit/client" + "github.com/pkg/errors" + "github.com/tonistiigi/buildx/driver" + "github.com/tonistiigi/buildx/util/progress" +) + +var buildkitImage = "moby/buildkit:master" // TODO: make this verified and configuratble + +type Driver struct { + driver.InitConfig + version dockertypes.Version +} + +func (d *Driver) Bootstrap(ctx context.Context, l progress.Logger) error { + return nil +} + +func (d *Driver) Info(ctx context.Context) (*driver.Info, error) { + _, err := d.DockerAPI.ServerVersion(ctx) + if err != nil { + return nil, errors.Wrapf(driver.ErrNotConnecting, err.Error()) + } + return &driver.Info{ + Status: driver.Running, + }, nil +} + +func (d *Driver) Stop(ctx context.Context, force bool) error { + return nil +} + +func (d *Driver) Rm(ctx context.Context, force bool) error { + return nil +} + +func (d *Driver) Client(ctx context.Context) (*client.Client, error) { + return client.New(ctx, "", client.WithDialer(func(string, time.Duration) (net.Conn, error) { + return d.DockerAPI.DialHijack(ctx, "/grpc", "h2c", nil) + })) +} diff --git a/driver/docker/factory.go b/driver/docker/factory.go new file mode 100644 index 00000000..37c60d23 --- /dev/null +++ b/driver/docker/factory.go @@ -0,0 +1,53 @@ +package docker + +import ( + "context" + + "github.com/pkg/errors" + "github.com/tonistiigi/buildx/driver" +) + +const prioritySupported = 10 +const priorityUnsupported = 99 + +func init() { + driver.Register(&factory{}) +} + +type factory struct { +} + +func (*factory) Name() string { + return "docker" +} + +func (*factory) Usage() string { + return "docker" +} + +func (*factory) Priority(cfg driver.InitConfig) int { + if cfg.DockerAPI == nil { + return priorityUnsupported + } + + c, err := cfg.DockerAPI.DialHijack(context.TODO(), "/grpc", "h2c", nil) + if err != nil { + return priorityUnsupported + } + c.Close() + + return prioritySupported +} + +func (*factory) New(ctx context.Context, cfg driver.InitConfig) (driver.Driver, error) { + if cfg.DockerAPI == nil { + return nil, errors.Errorf("docker driver requires docker API access") + } + + v, err := cfg.DockerAPI.ServerVersion(ctx) + if err != nil { + return nil, errors.Wrapf(driver.ErrNotConnecting, err.Error()) + } + + return &Driver{InitConfig: cfg, version: v}, nil +} diff --git a/driver/manager.go b/driver/manager.go index f3dd8ce5..624f7f7f 100644 --- a/driver/manager.go +++ b/driver/manager.go @@ -11,7 +11,7 @@ import ( type Factory interface { Name() string Usage() string - Priority() int // take initConfig? + Priority(cfg InitConfig) int New(ctx context.Context, cfg InitConfig) (Driver, error) } @@ -37,7 +37,7 @@ func Register(f Factory) { drivers[f.Name()] = f } -func GetDefaultFactory() (Factory, error) { +func GetDefaultFactory(ic InitConfig) (Factory, error) { if len(drivers) == 0 { return nil, errors.Errorf("no drivers available") } @@ -47,7 +47,7 @@ func GetDefaultFactory() (Factory, error) { } dd := make([]p, 0, len(drivers)) for _, f := range drivers { - dd = append(dd, p{f: f, priority: f.Priority()}) + dd = append(dd, p{f: f, priority: f.Priority(ic)}) } sort.Slice(dd, func(i, j int) bool { return dd[i].priority < dd[j].priority @@ -56,15 +56,16 @@ func GetDefaultFactory() (Factory, error) { } func GetDriver(ctx context.Context, name string, f Factory, api dockerclient.APIClient) (Driver, error) { + ic := InitConfig{ + DockerAPI: api, + Name: name, + } if f == nil { var err error - f, err = GetDefaultFactory() + f, err = GetDefaultFactory(ic) if err != nil { return nil, err } } - return f.New(ctx, InitConfig{ - Name: name, - DockerAPI: api, - }) + return f.New(ctx, ic) }