Passed
Push — master ( da7451...5b8a4a )
by Marcel
07:08
created

ShareService::create()   A

Complexity

Conditions 5
Paths 4

Size

Total Lines 20
Code Lines 12

Duplication

Lines 0
Ratio 0 %

Importance

Changes 2
Bugs 0 Features 0
Metric Value
cc 5
eloc 12
c 2
b 0
f 0
nc 4
nop 3
dl 0
loc 20
rs 9.5555
1
<?php
2
/**
3
 * Analytics
4
 *
5
 * This file is licensed under the Affero General Public License version 3 or
6
 * later. See the LICENSE.md file.
7
 *
8
 * @author Marcel Scherello <[email protected]>
9
 * @copyright 2021 Marcel Scherello
10
 */
11
12
namespace OCA\Analytics\Service;
13
14
use OCA\Analytics\Activity\ActivityManager;
15
use OCA\Analytics\Db\ShareMapper;
16
use OCP\IGroupManager;
17
use OCP\IUserManager;
18
use OCP\Security\ISecureRandom;
19
use Psr\Log\LoggerInterface;
20
21
class ShareService
22
{
23
    const SHARE_TYPE_USER = 0;
24
    const SHARE_TYPE_GROUP = 1;
25
    const SHARE_TYPE_USERGROUP = 2;
26
    const SHARE_TYPE_LINK = 3;
27
    const SHARE_TYPE_ROOM = 10;
28
29
    /** @var LoggerInterface */
30
    private $logger;
31
    /** @var ShareMapper */
32
    private $ShareMapper;
33
    private $secureRandom;
34
    private $ActivityManager;
35
    /** @var IGroupManager */
36
    private $groupManager;
37
    /** @var IUserManager */
38
    private $userManager;
39
40
    public function __construct(
41
        LoggerInterface $logger,
42
        ShareMapper $ShareMapper,
43
        ActivityManager $ActivityManager,
44
        IGroupManager $groupManager,
45
        ISecureRandom $secureRandom,
46
        IUserManager $userManager
47
    )
48
    {
49
        $this->logger = $logger;
50
        $this->ShareMapper = $ShareMapper;
51
        $this->secureRandom = $secureRandom;
52
        $this->groupManager = $groupManager;
53
        $this->ActivityManager = $ActivityManager;
54
        $this->userManager = $userManager;
55
    }
56
57
    /**
58
     * create a new share
59
     *
60
     * @NoAdminRequired
61
     * @param $datasetId
62
     * @param $type
63
     * @param $user
64
     * @return bool
65
     * @throws \OCP\DB\Exception
66
     */
67
    public function create($datasetId, $type, $user)
68
    {
69
        if ((int)$type === self::SHARE_TYPE_LINK) {
70
            $token = $this->generateToken();
71
            $this->ShareMapper->createShare($datasetId, $type, $user, $token);
72
        } elseif ((int)$type === self::SHARE_TYPE_USER) {
73
            $this->ShareMapper->createShare($datasetId, $type, $user, null);
74
        } elseif ((int)$type === self::SHARE_TYPE_GROUP) {
75
            // add the entry for the group
76
            $parent = $this->ShareMapper->createShare($datasetId, self::SHARE_TYPE_GROUP, $user, null);
77
78
            // add entries for every user of the group
79
            $usersInGroup = $this->groupManager->displayNamesInGroup($user);
80
            foreach ($usersInGroup as $userId => $displayName) {
81
                $this->ShareMapper->createShare($datasetId, self::SHARE_TYPE_USERGROUP, $userId, null, $parent);
82
            }
83
        }
84
85
        $this->ActivityManager->triggerEvent($datasetId, ActivityManager::OBJECT_DATASET, ActivityManager::SUBJECT_DATASET_SHARE);
86
        return true;
87
    }
88
89
    /**
90
     * get all shares for a dataset
91
     *
92
     * @NoAdminRequired
93
     * @param $datasetId
94
     * @return array
95
     */
96
    public function read($datasetId)
97
    {
98
        $shares = $this->ShareMapper->getShares($datasetId);
99
        foreach ($shares as &$share) {
100
            if ($share['type'] === 0) {
101
                $share['displayName'] = $this->userManager->get($share['uid_owner'])->getDisplayName();
102
            }
103
            $share['pass'] = $share['pass'] !== null;
104
        }
105
        return $shares;
106
    }
107
108
    /**
109
     * get all dataset by token
110
     *
111
     * @NoAdminRequired
112
     * @param $token
113
     * @return array
114
     */
115
    public function getDatasetByToken($token)
116
    {
117
        return $this->ShareMapper->getDatasetByToken($token);
118
    }
119
120
    /**
121
     * verify password hahes
122
     *
123
     * @NoAdminRequired
124
     * @param $password
125
     * @param $sharePassword
126
     * @return bool
127
     */
128
    public function verifyPassword($password, $sharePassword)
129
    {
130
        return password_verify($password, $sharePassword);
131
    }
132
133
    /**
134
     * get all datasets shared with user
135
     *
136
     * @NoAdminRequired
137
     */
138
    public function getSharedDatasets()
139
    {
140
        $sharedDatasets = $this->ShareMapper->getSharedDatasets();
141
        foreach ($sharedDatasets as &$sharedDataset) {
142
            $sharedDataset['type'] = '99';
143
            $sharedDataset['parrent'] = '0';
144
        }
145
        return $sharedDatasets;
146
    }
147
148
    /**
149
     * get metadata of a dataset, shared with current user
150
     *
151
     * @NoAdminRequired
152
     * @param $id
153
     * @return array
154
     */
155
    public function getSharedDataset($id)
156
    {
157
        return $this->ShareMapper->getSharedDataset($id);
158
    }
159
160
    /**
161
     * delete a share
162
     *
163
     * @NoAdminRequired
164
     * @param $shareId
165
     * @return bool
166
     */
167
    public function delete($shareId)
168
    {
169
        $share = $this->ShareMapper->getShare($shareId);
170
        $type = $share['type'];
171
        $this->logger->error('share type: ' . $type);
172
        if ((int)$type === self::SHARE_TYPE_LINK) {
173
            $this->ShareMapper->deleteShare($shareId);
174
        } elseif ((int)$type === self::SHARE_TYPE_USER) {
175
            $this->ShareMapper->deleteShare($shareId);
176
        } elseif ((int)$type === self::SHARE_TYPE_USERGROUP) {
177
            $this->ShareMapper->deleteShare($shareId);
178
        } elseif ((int)$type === self::SHARE_TYPE_GROUP) {
179
            $this->ShareMapper->deleteShare($shareId);
180
            $this->ShareMapper->deleteShareByParent($shareId);
181
        }
182
        return true;
183
    }
184
185
    /**
186
     * delete all shares for a dataset
187
     *
188
     * @NoAdminRequired
189
     * @param $datasetId
190
     * @return bool
191
     */
192
    public function deleteShareByDataset($datasetId)
193
    {
194
        return $this->ShareMapper->deleteShareByDataset($datasetId);
195
    }
196
197
    /**
198
     * update/set share password
199
     *
200
     * @NoAdminRequired
201
     * @param $shareId
202
     * @param $password
203
     * @param $canEdit
204
     * @return bool
205
     */
206
    public function update($shareId, $password = null, $canEdit = null)
207
    {
208
        if ($password !== null) {
209
            $password = password_hash($password, PASSWORD_DEFAULT);
210
            return $this->ShareMapper->updateSharePassword($shareId, $password);
211
        }
212
        if ($canEdit !== null) {
213
            $canEdit === 'true' ? $canEdit = \OCP\Constants::PERMISSION_UPDATE : $canEdit = \OCP\Constants::PERMISSION_READ;
214
            return $this->ShareMapper->updateSharePermissions($shareId, $canEdit);
215
        }
216
    }
217
218
    /**
219
     * generate to token used to authenticate federated shares
220
     *
221
     * @return string
222
     */
223
    private function generateToken()
224
    {
225
        $token = $this->secureRandom->generate(
226
            15,
227
            ISecureRandom::CHAR_LOWER . ISecureRandom::CHAR_UPPER . ISecureRandom::CHAR_DIGITS);
228
        return $token;
229
    }
230
231
}