1<?php
2/**
3 * @author Robin Appelman <icewind@owncloud.com>
4 * @author Roeland Jago Douma <rullzer@owncloud.com>
5 *
6 * @copyright Copyright (c) 2018, ownCloud GmbH
7 * @license AGPL-3.0
8 *
9 * This code is free software: you can redistribute it and/or modify
10 * it under the terms of the GNU Affero General Public License, version 3,
11 * as published by the Free Software Foundation.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU Affero General Public License for more details.
17 *
18 * You should have received a copy of the GNU Affero General Public License, version 3,
19 * along with this program.  If not, see <http://www.gnu.org/licenses/>
20 *
21 */
22
23namespace OC\Files\Mount;
24
25use OCP\Files\Config\IHomeMountProvider;
26use OCP\Files\Storage\IStorageFactory;
27use OCP\IConfig;
28use OCP\IUser;
29
30/**
31 * Mount provider for object store home storages
32 */
33class ObjectHomeMountProvider implements IHomeMountProvider {
34	/**
35	 * @var IConfig
36	 */
37	private $config;
38
39	/**
40	 * ObjectStoreHomeMountProvider constructor.
41	 *
42	 * @param IConfig $config
43	 */
44	public function __construct(IConfig $config) {
45		$this->config = $config;
46	}
47
48	/**
49	 * Get the cache mount for a user
50	 *
51	 * @param IUser $user
52	 * @param IStorageFactory $loader
53	 * @return \OCP\Files\Mount\IMountPoint[]
54	 */
55	public function getHomeMountForUser(IUser $user, IStorageFactory $loader) {
56		$config = $this->getMultiBucketObjectStoreConfig($user);
57		if ($config === null) {
58			$config = $this->getSingleBucketObjectStoreConfig($user);
59		}
60
61		if ($config === null) {
62			return null;
63		}
64
65		return new MountPoint('\OC\Files\ObjectStore\HomeObjectStoreStorage', '/' . $user->getUID(), $config['arguments'], $loader);
66	}
67
68	/**
69	 * @param IUser $user
70	 * @return array|null
71	 */
72	private function getSingleBucketObjectStoreConfig(IUser $user) {
73		$config = $this->config->getSystemValue('objectstore');
74		if (!\is_array($config)) {
75			return null;
76		}
77
78		// sanity checks
79		if (empty($config['class'])) {
80			\OCP\Util::writeLog('files', 'No class given for objectstore', \OCP\Util::ERROR);
81		}
82		if (!isset($config['arguments'])) {
83			$config['arguments'] = [];
84		}
85		$config['arguments']['user'] = $user;
86		// instantiate object store implementation
87		$config['arguments']['objectstore'] = new $config['class']($config['arguments']);
88
89		return $config;
90	}
91
92	/**
93	 * @param IUser $user
94	 * @return array|null
95	 */
96	private function getMultiBucketObjectStoreConfig(IUser $user) {
97		$config = $this->config->getSystemValue('objectstore_multibucket');
98		if (!\is_array($config)) {
99			return null;
100		}
101
102		// sanity checks
103		if (empty($config['class'])) {
104			\OCP\Util::writeLog('files', 'No class given for objectstore', \OCP\Util::ERROR);
105		}
106		if (!isset($config['arguments'])) {
107			$config['arguments'] = [];
108		}
109		$config['arguments']['user'] = $user;
110
111		$bucket = $this->config->getUserValue($user->getUID(), 'homeobjectstore', 'bucket', null);
112
113		if ($bucket === null) {
114			/*
115			 * Use any provided bucket argument as prefix
116			 * and add the mapping from username => bucket
117			 */
118			if (!isset($config['arguments']['bucket'])) {
119				$config['arguments']['bucket'] = '';
120			}
121			if (isset($config['arguments']['mapper-class'])) {
122				$mapperClass = $config['arguments']['mapper-class'];
123				$mapper = new $mapperClass($user);
124			} else {
125				$mapper = new \OC\Files\ObjectStore\Mapper($user);
126			}
127			$config['arguments']['bucket'] .= $mapper->getBucket();
128
129			$this->config->setUserValue($user->getUID(), 'homeobjectstore', 'bucket', $config['arguments']['bucket']);
130		} else {
131			$config['arguments']['bucket'] = $bucket;
132		}
133
134		// instantiate object store implementation
135		$config['arguments']['objectstore'] = new $config['class']($config['arguments']);
136
137		return $config;
138	}
139}
140