Skip to content

Commit 22c0705

Browse files
refactor(storage): refactoring storage
Signed-off-by: Laurentiu Niculae <niculae.laurentiu1@gmail.com>
1 parent 6014813 commit 22c0705

45 files changed

Lines changed: 846 additions & 747 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

pkg/api/config/config.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ import (
88
distspec "github.com/opencontainers/distribution-spec/specs-go"
99

1010
extconf "zotregistry.io/zot/pkg/extensions/config"
11-
"zotregistry.io/zot/pkg/storage"
11+
storageConstants "zotregistry.io/zot/pkg/storage/constants"
1212
)
1313

1414
var (
@@ -147,7 +147,7 @@ func New() *Config {
147147
ReleaseTag: ReleaseTag,
148148
BinaryType: BinaryType,
149149
Storage: GlobalStorageConfig{
150-
StorageConfig: StorageConfig{GC: true, GCDelay: storage.DefaultGCDelay, Dedupe: true},
150+
StorageConfig: StorageConfig{GC: true, GCDelay: storageConstants.DefaultGCDelay, Dedupe: true},
151151
},
152152
HTTP: HTTPConfig{Address: "127.0.0.1", Port: "8080", Auth: &AuthConfig{FailDelay: 0}},
153153
Log: &LogConfig{Level: "debug"},

pkg/api/controller.go

Lines changed: 5 additions & 230 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,6 @@ import (
1414
"syscall"
1515
"time"
1616

17-
"github.com/docker/distribution/registry/storage/driver/factory"
1817
"github.com/gorilla/handlers"
1918
"github.com/gorilla/mux"
2019

@@ -27,10 +26,6 @@ import (
2726
"zotregistry.io/zot/pkg/meta/repodb/repodbfactory"
2827
"zotregistry.io/zot/pkg/scheduler"
2928
"zotregistry.io/zot/pkg/storage"
30-
"zotregistry.io/zot/pkg/storage/cache"
31-
"zotregistry.io/zot/pkg/storage/constants"
32-
"zotregistry.io/zot/pkg/storage/local"
33-
"zotregistry.io/zot/pkg/storage/s3"
3429
)
3530

3631
const (
@@ -224,7 +219,7 @@ func (c *Controller) Init(reloadCtx context.Context) error {
224219

225220
c.Metrics = monitoring.NewMetricsServer(enabled, c.Log)
226221

227-
if err := c.InitImageStore(reloadCtx); err != nil {
222+
if err := c.InitImageStore(); err != nil { //nolint:contextcheck
228223
return err
229224
}
230225

@@ -244,235 +239,15 @@ func (c *Controller) InitCVEInfo() {
244239
}
245240
}
246241

247-
func (c *Controller) InitImageStore(ctx context.Context) error {
248-
c.StoreController = storage.StoreController{}
249-
242+
func (c *Controller) InitImageStore() error {
250243
linter := ext.GetLinter(c.Config, c.Log)
251244

252-
if c.Config.Storage.RootDirectory != "" {
253-
// no need to validate hard links work on s3
254-
if c.Config.Storage.Dedupe && c.Config.Storage.StorageDriver == nil {
255-
err := local.ValidateHardLink(c.Config.Storage.RootDirectory)
256-
if err != nil {
257-
c.Log.Warn().Msg("input storage root directory filesystem does not supports hardlinking," +
258-
"disabling dedupe functionality")
259-
260-
c.Config.Storage.Dedupe = false
261-
}
262-
}
263-
264-
var defaultStore storage.ImageStore
265-
if c.Config.Storage.StorageDriver == nil {
266-
// false positive lint - linter does not implement Lint method
267-
//nolint:typecheck,contextcheck
268-
defaultStore = local.NewImageStore(c.Config.Storage.RootDirectory,
269-
c.Config.Storage.GC, c.Config.Storage.GCDelay,
270-
c.Config.Storage.Dedupe, c.Config.Storage.Commit, c.Log, c.Metrics, linter,
271-
CreateCacheDatabaseDriver(c.Config.Storage.StorageConfig, c.Log),
272-
)
273-
} else {
274-
storeName := fmt.Sprintf("%v", c.Config.Storage.StorageDriver["name"])
275-
if storeName != storage.S3StorageDriverName {
276-
c.Log.Fatal().Err(errors.ErrBadConfig).Str("storageDriver", storeName).
277-
Msg("unsupported storage driver")
278-
}
279-
// Init a Storager from connection string.
280-
store, err := factory.Create(storeName, c.Config.Storage.StorageDriver)
281-
if err != nil {
282-
c.Log.Error().Err(err).Str("rootDir", c.Config.Storage.RootDirectory).Msg("unable to create s3 service")
283-
284-
return err
285-
}
286-
287-
/* in the case of s3 c.Config.Storage.RootDirectory is used for caching blobs locally and
288-
c.Config.Storage.StorageDriver["rootdirectory"] is the actual rootDir in s3 */
289-
rootDir := "/"
290-
if c.Config.Storage.StorageDriver["rootdirectory"] != nil {
291-
rootDir = fmt.Sprintf("%v", c.Config.Storage.StorageDriver["rootdirectory"])
292-
}
293-
294-
// false positive lint - linter does not implement Lint method
295-
//nolint: typecheck,contextcheck
296-
defaultStore = s3.NewImageStore(rootDir, c.Config.Storage.RootDirectory,
297-
c.Config.Storage.GC, c.Config.Storage.GCDelay, c.Config.Storage.Dedupe,
298-
c.Config.Storage.Commit, c.Log, c.Metrics, linter, store,
299-
CreateCacheDatabaseDriver(c.Config.Storage.StorageConfig, c.Log))
300-
}
301-
302-
c.StoreController.DefaultStore = defaultStore
303-
} else {
304-
// we can't proceed without global storage
305-
c.Log.Error().Err(errors.ErrImgStoreNotFound).Msg("controller: no storage config provided")
306-
307-
return errors.ErrImgStoreNotFound
308-
}
309-
310-
if c.Config.Storage.SubPaths != nil {
311-
if len(c.Config.Storage.SubPaths) > 0 {
312-
subPaths := c.Config.Storage.SubPaths
313-
314-
//nolint: contextcheck
315-
subImageStore, err := c.getSubStore(subPaths, linter)
316-
if err != nil {
317-
c.Log.Error().Err(err).Msg("controller: error getting sub image store")
318-
319-
return err
320-
}
321-
322-
c.StoreController.SubStore = subImageStore
323-
}
324-
}
325-
326-
return nil
327-
}
328-
329-
func (c *Controller) getSubStore(subPaths map[string]config.StorageConfig,
330-
linter storage.Lint,
331-
) (map[string]storage.ImageStore, error) {
332-
imgStoreMap := make(map[string]storage.ImageStore, 0)
333-
334-
subImageStore := make(map[string]storage.ImageStore)
335-
336-
// creating image store per subpaths
337-
for route, storageConfig := range subPaths {
338-
// no need to validate hard links work on s3
339-
if storageConfig.Dedupe && storageConfig.StorageDriver == nil {
340-
err := local.ValidateHardLink(storageConfig.RootDirectory)
341-
if err != nil {
342-
c.Log.Warn().Msg("input storage root directory filesystem does not supports hardlinking, " +
343-
"disabling dedupe functionality")
344-
345-
storageConfig.Dedupe = false
346-
}
347-
}
348-
349-
if storageConfig.StorageDriver == nil {
350-
// Compare if subpath root dir is same as default root dir
351-
isSame, _ := config.SameFile(c.Config.Storage.RootDirectory, storageConfig.RootDirectory)
352-
353-
if isSame {
354-
c.Log.Error().Err(errors.ErrBadConfig).Msg("sub path storage directory is same as root directory")
355-
356-
return nil, errors.ErrBadConfig
357-
}
358-
359-
isUnique := true
360-
361-
// Compare subpath unique files
362-
for file := range imgStoreMap {
363-
// We already have image storage for this file
364-
if compareImageStore(file, storageConfig.RootDirectory) {
365-
subImageStore[route] = imgStoreMap[file]
366-
367-
isUnique = true
368-
}
369-
}
370-
371-
// subpath root directory is unique
372-
// add it to uniqueSubFiles
373-
// Create a new image store and assign it to imgStoreMap
374-
if isUnique {
375-
imgStoreMap[storageConfig.RootDirectory] = local.NewImageStore(storageConfig.RootDirectory,
376-
storageConfig.GC, storageConfig.GCDelay, storageConfig.Dedupe,
377-
storageConfig.Commit, c.Log, c.Metrics, linter, CreateCacheDatabaseDriver(storageConfig, c.Log))
378-
379-
subImageStore[route] = imgStoreMap[storageConfig.RootDirectory]
380-
}
381-
} else {
382-
storeName := fmt.Sprintf("%v", storageConfig.StorageDriver["name"])
383-
if storeName != storage.S3StorageDriverName {
384-
c.Log.Fatal().Err(errors.ErrBadConfig).Str("storageDriver", storeName).
385-
Msg("unsupported storage driver")
386-
}
387-
388-
// Init a Storager from connection string.
389-
store, err := factory.Create(storeName, storageConfig.StorageDriver)
390-
if err != nil {
391-
c.Log.Error().Err(err).Str("rootDir", storageConfig.RootDirectory).Msg("Unable to create s3 service")
392-
393-
return nil, err
394-
}
395-
396-
/* in the case of s3 c.Config.Storage.RootDirectory is used for caching blobs locally and
397-
c.Config.Storage.StorageDriver["rootdirectory"] is the actual rootDir in s3 */
398-
rootDir := "/"
399-
if c.Config.Storage.StorageDriver["rootdirectory"] != nil {
400-
rootDir = fmt.Sprintf("%v", c.Config.Storage.StorageDriver["rootdirectory"])
401-
}
402-
403-
// false positive lint - linter does not implement Lint method
404-
//nolint: typecheck
405-
subImageStore[route] = s3.NewImageStore(rootDir, storageConfig.RootDirectory,
406-
storageConfig.GC, storageConfig.GCDelay,
407-
storageConfig.Dedupe, storageConfig.Commit, c.Log, c.Metrics, linter, store,
408-
CreateCacheDatabaseDriver(storageConfig, c.Log),
409-
)
410-
}
411-
}
412-
413-
return subImageStore, nil
414-
}
415-
416-
func compareImageStore(root1, root2 string) bool {
417-
isSameFile, err := config.SameFile(root1, root2)
418-
// This error is path error that means either of root directory doesn't exist, in that case do string match
245+
storeController, err := storage.New(c.Config, linter, c.Metrics, c.Log)
419246
if err != nil {
420-
return strings.EqualFold(root1, root2)
247+
return err
421248
}
422249

423-
return isSameFile
424-
}
425-
426-
func getUseRelPaths(storageConfig *config.StorageConfig) bool {
427-
return storageConfig.StorageDriver == nil
428-
}
429-
430-
func CreateCacheDatabaseDriver(storageConfig config.StorageConfig, log log.Logger) cache.Cache {
431-
if storageConfig.Dedupe || storageConfig.StorageDriver != nil {
432-
if !storageConfig.RemoteCache {
433-
params := cache.BoltDBDriverParameters{}
434-
params.RootDir = storageConfig.RootDirectory
435-
params.Name = constants.BoltdbName
436-
437-
if storageConfig.StorageDriver != nil {
438-
params.Name = s3.CacheDBName
439-
}
440-
441-
params.UseRelPaths = getUseRelPaths(&storageConfig)
442-
443-
driver, _ := storage.Create("boltdb", params, log)
444-
445-
return driver
446-
}
447-
448-
// remote cache
449-
if storageConfig.CacheDriver != nil {
450-
name, ok := storageConfig.CacheDriver["name"].(string)
451-
if !ok {
452-
log.Warn().Msg("remote cache driver name missing!")
453-
454-
return nil
455-
}
456-
457-
if name != constants.DynamoDBDriverName {
458-
log.Warn().Str("driver", name).Msg("remote cache driver unsupported!")
459-
460-
return nil
461-
}
462-
463-
// dynamodb
464-
dynamoParams := cache.DynamoDBDriverParameters{}
465-
dynamoParams.Endpoint, _ = storageConfig.CacheDriver["endpoint"].(string)
466-
dynamoParams.Region, _ = storageConfig.CacheDriver["region"].(string)
467-
dynamoParams.TableName, _ = storageConfig.CacheDriver["cachetablename"].(string)
468-
469-
driver, _ := storage.Create("dynamodb", dynamoParams, log)
470-
471-
return driver
472-
}
473-
474-
return nil
475-
}
250+
c.StoreController = storeController
476251

477252
return nil
478253
}

0 commit comments

Comments
 (0)