diff --git a/phpBB/phpbb/storage/adapter/adapter_interface.php b/phpBB/phpbb/storage/adapter/adapter_interface.php
index 70eb6f1cc7..c92a429ec8 100644
--- a/phpBB/phpbb/storage/adapter/adapter_interface.php
+++ b/phpBB/phpbb/storage/adapter/adapter_interface.php
@@ -15,6 +15,13 @@ namespace phpbb\storage\adapter;
 
 interface adapter_interface
 {
+	/**
+	 * Set adapter parameters
+	 *
+	 * @param array	options		Storage-specific options.
+	 */
+	public function configure($options);
+
 	/**
 	 * Dumps content into a file.
 	 *
diff --git a/phpBB/phpbb/storage/adapter/local.php b/phpBB/phpbb/storage/adapter/local.php
index 68b9ce0c2c..1d229abf7b 100644
--- a/phpBB/phpbb/storage/adapter/local.php
+++ b/phpBB/phpbb/storage/adapter/local.php
@@ -15,7 +15,6 @@ namespace phpbb\storage\adapter;
 
 use phpbb\storage\exception\exception;
 use phpbb\filesystem\exception\filesystem_exception;
-use phpbb\config\config;
 use phpbb\filesystem\filesystem;
 
 /**
@@ -30,16 +29,27 @@ class local implements adapter_interface
 	 */
 	protected $filesystem;
 
+	/** @var string path */
+	protected $phpbb_root_path;
+
 	/** @var string path */
 	protected $root_path;
 
 	/**
 	 * Constructor
 	 */
-	public function __construct(config $config, filesystem $filesystem, $phpbb_root_path, $path_key)
+	public function __construct(filesystem $filesystem, $phpbb_root_path)
 	{
 		$this->filesystem = $filesystem;
-		$this->root_path = $phpbb_root_path . $config[$path_key];
+		$this->phpbb_root_path = $phpbb_root_path;
+	}
+
+	/**
+	 * {@inheritdoc}
+	 */
+	public function configure($options)
+	{
+		$this->root_path = $this->phpbb_root_path . $options['path'];
 
 		if (substr($this->root_path, -1, 1) != DIRECTORY_SEPARATOR)
 		{
diff --git a/phpBB/phpbb/storage/adapter_factory.php b/phpBB/phpbb/storage/adapter_factory.php
new file mode 100644
index 0000000000..b63a10fea6
--- /dev/null
+++ b/phpBB/phpbb/storage/adapter_factory.php
@@ -0,0 +1,57 @@
+<?php
+/**
+ *
+ * This file is part of the phpBB Forum Software package.
+ *
+ * @copyright (c) phpBB Limited <https://www.phpbb.com>
+ * @license GNU General Public License, version 2 (GPL-2.0)
+ *
+ * For full copyright and license information, please see
+ * the docs/CREDITS.txt file.
+ *
+ */
+
+namespace phpbb\storage;
+
+use phpbb\config\config;
+use phpbb\di\service_collection;
+use Symfony\Component\DependencyInjection\ContainerInterface;
+
+class adapter_factory
+{
+	protected $config;
+	protected $container;
+	protected $adapters;
+	protected $providers;
+
+	public function __construct(config $config, ContainerInterface $container, service_collection $adapters, service_collection $providers)
+	{
+		$this->config = $config;
+		$this->container = $container;
+		$this->adapters = $adapters;
+		$this->providers = $providers;
+	}
+
+	public function get($storage_name)
+	{
+		$provider_class = $this->config['storage\\' . $storage_name . '\\adapter'];
+		$provider = $this->providers->get_by_class($provider_class);
+
+		$adapter = $this->adapters->get_by_class($provider->get_class());
+		$adapter->configure($this->build_options($storage_name, $provider->get_options()));
+
+		return $adapter;
+	}
+
+	public function build_options($storage_name, array $definitions)
+	{
+		$options = [];
+
+		foreach ($definitions as $def)
+		{
+			$options[$def] = $this->config['storage\\' . $storage_name . '\\config\\' . $def];
+		}
+
+		return $options;
+	}
+}
diff --git a/phpBB/phpbb/storage/provider/local.php b/phpBB/phpbb/storage/provider/local.php
new file mode 100644
index 0000000000..6369c626c7
--- /dev/null
+++ b/phpBB/phpbb/storage/provider/local.php
@@ -0,0 +1,27 @@
+<?php
+/**
+ *
+ * This file is part of the phpBB Forum Software package.
+ *
+ * @copyright (c) phpBB Limited <https://www.phpbb.com>
+ * @license GNU General Public License, version 2 (GPL-2.0)
+ *
+ * For full copyright and license information, please see
+ * the docs/CREDITS.txt file.
+ *
+ */
+
+namespace phpbb\storage\provider;
+
+class local implements provider_interface
+{
+	public function get_class()
+	{
+		return \phpbb\storage\adapter\local::class;
+	}
+
+	public function get_options()
+	{
+		return ['path'];
+	}
+}
diff --git a/phpBB/phpbb/storage/provider/provider_interface.php b/phpBB/phpbb/storage/provider/provider_interface.php
new file mode 100644
index 0000000000..4d9a550e9a
--- /dev/null
+++ b/phpBB/phpbb/storage/provider/provider_interface.php
@@ -0,0 +1,20 @@
+<?php
+/**
+ *
+ * This file is part of the phpBB Forum Software package.
+ *
+ * @copyright (c) phpBB Limited <https://www.phpbb.com>
+ * @license GNU General Public License, version 2 (GPL-2.0)
+ *
+ * For full copyright and license information, please see
+ * the docs/CREDITS.txt file.
+ *
+ */
+
+namespace phpbb\storage\provider;
+
+interface provider_interface
+{
+	public function get_class();
+	public function get_options();
+}
diff --git a/phpBB/phpbb/storage/storage.php b/phpBB/phpbb/storage/storage.php
index f532f4d95f..04a66396e8 100644
--- a/phpBB/phpbb/storage/storage.php
+++ b/phpBB/phpbb/storage/storage.php
@@ -20,9 +20,9 @@ class storage
 {
 	protected $adapter;
 
-	public function __construct($adapter)
+	public function __construct($factory, $storage_name)
 	{
-		$this->adapter = $adapter;
+		$this->adapter = $factory->get($storage_name);
 	}
 
 	public function put_contents($path, $content)