| package factory |
| |
| import ( |
| "fmt" |
| |
| storagedriver "github.com/docker/distribution/registry/storage/driver" |
| ) |
| |
| // driverFactories stores an internal mapping between storage driver names and their respective |
| // factories |
| var driverFactories = make(map[string]StorageDriverFactory) |
| |
| // StorageDriverFactory is a factory interface for creating storagedriver.StorageDriver interfaces |
| // Storage drivers should call Register() with a factory to make the driver available by name. |
| // Individual StorageDriver implementations generally register with the factory via the Register |
| // func (below) in their init() funcs, and as such they should be imported anonymously before use. |
| // See below for an example of how to register and get a StorageDriver for S3 |
| // |
| // import _ "github.com/docker/distribution/registry/storage/driver/s3-aws" |
| // s3Driver, err = factory.Create("s3", storageParams) |
| // // assuming no error, s3Driver is the StorageDriver that communicates with S3 according to storageParams |
| type StorageDriverFactory interface { |
| // Create returns a new storagedriver.StorageDriver with the given parameters |
| // Parameters will vary by driver and may be ignored |
| // Each parameter key must only consist of lowercase letters and numbers |
| Create(parameters map[string]interface{}) (storagedriver.StorageDriver, error) |
| } |
| |
| // Register makes a storage driver available by the provided name. |
| // If Register is called twice with the same name or if driver factory is nil, it panics. |
| // Additionally, it is not concurrency safe. Most Storage Drivers call this function |
| // in their init() functions. See the documentation for StorageDriverFactory for more. |
| func Register(name string, factory StorageDriverFactory) { |
| if factory == nil { |
| panic("Must not provide nil StorageDriverFactory") |
| } |
| _, registered := driverFactories[name] |
| if registered { |
| panic(fmt.Sprintf("StorageDriverFactory named %s already registered", name)) |
| } |
| |
| driverFactories[name] = factory |
| } |
| |
| // Create a new storagedriver.StorageDriver with the given name and |
| // parameters. To use a driver, the StorageDriverFactory must first be |
| // registered with the given name. If no drivers are found, an |
| // InvalidStorageDriverError is returned |
| func Create(name string, parameters map[string]interface{}) (storagedriver.StorageDriver, error) { |
| driverFactory, ok := driverFactories[name] |
| if !ok { |
| return nil, InvalidStorageDriverError{name} |
| } |
| return driverFactory.Create(parameters) |
| } |
| |
| // InvalidStorageDriverError records an attempt to construct an unregistered storage driver |
| type InvalidStorageDriverError struct { |
| Name string |
| } |
| |
| func (err InvalidStorageDriverError) Error() string { |
| return fmt.Sprintf("StorageDriver not registered: %s", err.Name) |
| } |