github.com/zhouyu0/docker-note@v0.0.0-20190722021225-b8d3825084db/builder/builder-next/controller.go (about) 1 package buildkit 2 3 import ( 4 "net/http" 5 "os" 6 "path/filepath" 7 8 "github.com/containerd/containerd/content/local" 9 "github.com/docker/docker/api/types" 10 "github.com/docker/docker/builder/builder-next/adapters/containerimage" 11 "github.com/docker/docker/builder/builder-next/adapters/snapshot" 12 containerimageexp "github.com/docker/docker/builder/builder-next/exporter" 13 "github.com/docker/docker/builder/builder-next/imagerefchecker" 14 mobyworker "github.com/docker/docker/builder/builder-next/worker" 15 "github.com/docker/docker/daemon/config" 16 "github.com/docker/docker/daemon/graphdriver" 17 units "github.com/docker/go-units" 18 "github.com/moby/buildkit/cache" 19 "github.com/moby/buildkit/cache/metadata" 20 registryremotecache "github.com/moby/buildkit/cache/remotecache/registry" 21 "github.com/moby/buildkit/client" 22 "github.com/moby/buildkit/control" 23 "github.com/moby/buildkit/exporter" 24 "github.com/moby/buildkit/frontend" 25 dockerfile "github.com/moby/buildkit/frontend/dockerfile/builder" 26 "github.com/moby/buildkit/frontend/gateway" 27 "github.com/moby/buildkit/frontend/gateway/forwarder" 28 "github.com/moby/buildkit/snapshot/blobmapping" 29 "github.com/moby/buildkit/solver/bboltcachestorage" 30 "github.com/moby/buildkit/worker" 31 "github.com/pkg/errors" 32 ) 33 34 func newController(rt http.RoundTripper, opt Opt) (*control.Controller, error) { 35 if err := os.MkdirAll(opt.Root, 0700); err != nil { 36 return nil, err 37 } 38 39 dist := opt.Dist 40 root := opt.Root 41 42 var driver graphdriver.Driver 43 if ls, ok := dist.LayerStore.(interface { 44 Driver() graphdriver.Driver 45 }); ok { 46 driver = ls.Driver() 47 } else { 48 return nil, errors.Errorf("could not access graphdriver") 49 } 50 51 sbase, err := snapshot.NewSnapshotter(snapshot.Opt{ 52 GraphDriver: driver, 53 LayerStore: dist.LayerStore, 54 Root: root, 55 }) 56 if err != nil { 57 return nil, err 58 } 59 60 store, err := local.NewStore(filepath.Join(root, "content")) 61 if err != nil { 62 return nil, err 63 } 64 store = &contentStoreNoLabels{store} 65 66 md, err := metadata.NewStore(filepath.Join(root, "metadata.db")) 67 if err != nil { 68 return nil, err 69 } 70 71 snapshotter := blobmapping.NewSnapshotter(blobmapping.Opt{ 72 Content: store, 73 Snapshotter: sbase, 74 MetadataStore: md, 75 }) 76 77 layerGetter, ok := sbase.(imagerefchecker.LayerGetter) 78 if !ok { 79 return nil, errors.Errorf("snapshotter does not implement layergetter") 80 } 81 82 refChecker := imagerefchecker.New(imagerefchecker.Opt{ 83 ImageStore: dist.ImageStore, 84 LayerGetter: layerGetter, 85 }) 86 87 cm, err := cache.NewManager(cache.ManagerOpt{ 88 Snapshotter: snapshotter, 89 MetadataStore: md, 90 PruneRefChecker: refChecker, 91 }) 92 if err != nil { 93 return nil, err 94 } 95 96 src, err := containerimage.NewSource(containerimage.SourceOpt{ 97 SessionManager: opt.SessionManager, 98 CacheAccessor: cm, 99 ContentStore: store, 100 DownloadManager: dist.DownloadManager, 101 MetadataStore: dist.V2MetadataService, 102 ImageStore: dist.ImageStore, 103 ReferenceStore: dist.ReferenceStore, 104 ResolverOpt: opt.ResolverOpt, 105 }) 106 if err != nil { 107 return nil, err 108 } 109 110 exec, err := newExecutor(root, opt.DefaultCgroupParent, opt.NetworkController) 111 if err != nil { 112 return nil, err 113 } 114 115 differ, ok := sbase.(containerimageexp.Differ) 116 if !ok { 117 return nil, errors.Errorf("snapshotter doesn't support differ") 118 } 119 120 exp, err := containerimageexp.New(containerimageexp.Opt{ 121 ImageStore: dist.ImageStore, 122 ReferenceStore: dist.ReferenceStore, 123 Differ: differ, 124 }) 125 if err != nil { 126 return nil, err 127 } 128 129 cacheStorage, err := bboltcachestorage.NewStore(filepath.Join(opt.Root, "cache.db")) 130 if err != nil { 131 return nil, err 132 } 133 134 gcPolicy, err := getGCPolicy(opt.BuilderConfig, root) 135 if err != nil { 136 return nil, errors.Wrap(err, "could not get builder GC policy") 137 } 138 139 wopt := mobyworker.Opt{ 140 ID: "moby", 141 SessionManager: opt.SessionManager, 142 MetadataStore: md, 143 ContentStore: store, 144 CacheManager: cm, 145 GCPolicy: gcPolicy, 146 Snapshotter: snapshotter, 147 Executor: exec, 148 ImageSource: src, 149 DownloadManager: dist.DownloadManager, 150 V2MetadataService: dist.V2MetadataService, 151 Exporters: map[string]exporter.Exporter{ 152 "moby": exp, 153 }, 154 Transport: rt, 155 } 156 157 wc := &worker.Controller{} 158 w, err := mobyworker.NewWorker(wopt) 159 if err != nil { 160 return nil, err 161 } 162 wc.Add(w) 163 164 frontends := map[string]frontend.Frontend{ 165 "dockerfile.v0": forwarder.NewGatewayForwarder(wc, dockerfile.Build), 166 "gateway.v0": gateway.NewGatewayFrontend(wc), 167 } 168 169 return control.NewController(control.Opt{ 170 SessionManager: opt.SessionManager, 171 WorkerController: wc, 172 Frontends: frontends, 173 CacheKeyStorage: cacheStorage, 174 ResolveCacheImporterFunc: registryremotecache.ResolveCacheImporterFunc(opt.SessionManager, opt.ResolverOpt), 175 // TODO: set ResolveCacheExporterFunc for exporting cache 176 }) 177 } 178 179 func getGCPolicy(conf config.BuilderConfig, root string) ([]client.PruneInfo, error) { 180 var gcPolicy []client.PruneInfo 181 if conf.GC.Enabled { 182 var ( 183 defaultKeepStorage int64 184 err error 185 ) 186 187 if conf.GC.DefaultKeepStorage != "" { 188 defaultKeepStorage, err = units.RAMInBytes(conf.GC.DefaultKeepStorage) 189 if err != nil { 190 return nil, errors.Wrapf(err, "could not parse '%s' as Builder.GC.DefaultKeepStorage config", conf.GC.DefaultKeepStorage) 191 } 192 } 193 194 if conf.GC.Policy == nil { 195 gcPolicy = mobyworker.DefaultGCPolicy(root, defaultKeepStorage) 196 } else { 197 gcPolicy = make([]client.PruneInfo, len(conf.GC.Policy)) 198 for i, p := range conf.GC.Policy { 199 b, err := units.RAMInBytes(p.KeepStorage) 200 if err != nil { 201 return nil, err 202 } 203 if b == 0 { 204 b = defaultKeepStorage 205 } 206 gcPolicy[i], err = toBuildkitPruneInfo(types.BuildCachePruneOptions{ 207 All: p.All, 208 KeepStorage: b, 209 Filters: p.Filter, 210 }) 211 if err != nil { 212 return nil, err 213 } 214 } 215 } 216 } 217 return gcPolicy, nil 218 }