Completed
Push — master ( c20409...a4266f )
by Lukas
07:37
created

AbstractMapping::setDNbyUUID()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 9
Code Lines 4

Duplication

Lines 9
Ratio 100 %

Importance

Changes 0
Metric Value
cc 1
eloc 4
nc 1
nop 2
dl 9
loc 9
rs 9.6666
c 0
b 0
f 0
1
<?php
2
/**
3
 * @copyright Copyright (c) 2016, ownCloud, Inc.
4
 *
5
 * @author Aaron Wood <[email protected]>
6
 * @author Arthur Schiwon <[email protected]>
7
 * @author Morris Jobke <[email protected]>
8
 *
9
 * @license AGPL-3.0
10
 *
11
 * This code is free software: you can redistribute it and/or modify
12
 * it under the terms of the GNU Affero General Public License, version 3,
13
 * as published by the Free Software Foundation.
14
 *
15
 * This program is distributed in the hope that it will be useful,
16
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18
 * GNU Affero General Public License for more details.
19
 *
20
 * You should have received a copy of the GNU Affero General Public License, version 3,
21
 * along with this program.  If not, see <http://www.gnu.org/licenses/>
22
 *
23
 */
24
25
namespace OCA\User_LDAP\Mapping;
26
27
/**
28
* Class AbstractMapping
29
* @package OCA\User_LDAP\Mapping
30
*/
31
abstract class AbstractMapping {
32
	/**
33
	 * @var \OCP\IDBConnection $dbc
34
	 */
35
	protected $dbc;
36
37
	/**
38
	 * returns the DB table name which holds the mappings
39
	 * @return string
40
	 */
41
	abstract protected function getTableName();
42
43
	/**
44
	 * @param \OCP\IDBConnection $dbc
45
	 */
46
	public function __construct(\OCP\IDBConnection $dbc) {
47
		$this->dbc = $dbc;
48
	}
49
50
	/**
51
	 * checks whether a provided string represents an existing table col
52
	 * @param string $col
53
	 * @return bool
54
	 */
55
	public function isColNameValid($col) {
56
		switch($col) {
57
			case 'ldap_dn':
58
			case 'owncloud_name':
59
			case 'directory_uuid':
60
				return true;
61
			default:
62
				return false;
63
		}
64
	}
65
66
	/**
67
	 * Gets the value of one column based on a provided value of another column
68
	 * @param string $fetchCol
69
	 * @param string $compareCol
70
	 * @param string $search
71
	 * @throws \Exception
72
	 * @return string|false
73
	 */
74
	protected function getXbyY($fetchCol, $compareCol, $search) {
75
		if(!$this->isColNameValid($fetchCol)) {
76
			//this is used internally only, but we don't want to risk
77
			//having SQL injection at all.
78
			throw new \Exception('Invalid Column Name');
79
		}
80
		$query = $this->dbc->prepare('
81
			SELECT `' . $fetchCol . '`
82
			FROM `'. $this->getTableName() .'`
83
			WHERE `' . $compareCol . '` = ?
84
		');
85
86
		$res = $query->execute(array($search));
87
		if($res !== false) {
88
			return $query->fetchColumn();
89
		}
90
91
		return false;
92
	}
93
94
	/**
95
	 * Performs a DELETE or UPDATE query to the database.
96
	 * @param \Doctrine\DBAL\Driver\Statement $query
97
	 * @param array $parameters
98
	 * @return bool true if at least one row was modified, false otherwise
99
	 */
100
	protected function modify($query, $parameters) {
101
		$result = $query->execute($parameters);
102
		return ($result === true && $query->rowCount() > 0);
103
	}
104
105
	/**
106
	 * Gets the LDAP DN based on the provided name.
107
	 * Replaces Access::ocname2dn
108
	 * @param string $name
109
	 * @return string|false
110
	 */
111
	public function getDNByName($name) {
112
		return $this->getXbyY('ldap_dn', 'owncloud_name', $name);
113
	}
114
115
	/**
116
	 * Updates the DN based on the given UUID
117
	 * @param string $fdn
118
	 * @param string $uuid
119
	 * @return bool
120
	 */
121 View Code Duplication
	public function setDNbyUUID($fdn, $uuid) {
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
122
		$query = $this->dbc->prepare('
123
			UPDATE `' . $this->getTableName() . '`
124
			SET `ldap_dn` = ?
125
			WHERE `directory_uuid` = ?
126
		');
127
128
		return $this->modify($query, array($fdn, $uuid));
129
	}
130
131
	/**
132
	 * Updates the UUID based on the given DN
133
	 *
134
	 * required by Migration/UUIDFix
135
	 *
136
	 * @param $uuid
137
	 * @param $fdn
138
	 * @return bool
139
	 */
140 View Code Duplication
	public function setUUIDbyDN($uuid, $fdn) {
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
141
		$query = $this->dbc->prepare('
142
			UPDATE `' . $this->getTableName() . '`
143
			SET `directory_uuid` = ?
144
			WHERE `ldap_dn` = ?
145
		');
146
147
		return $this->modify($query, [$uuid, $fdn]);
148
	}
149
150
	/**
151
	 * Gets the name based on the provided LDAP DN.
152
	 * @param string $fdn
153
	 * @return string|false
154
	 */
155
	public function getNameByDN($fdn) {
156
		return $this->getXbyY('owncloud_name', 'ldap_dn', $fdn);
157
	}
158
159
	/**
160
	 * Searches mapped names by the giving string in the name column
161
	 * @param string $search
162
	 * @param string $prefixMatch
163
	 * @param string $postfixMatch
164
	 * @return string[]
165
	 */
166
	public function getNamesBySearch($search, $prefixMatch = "", $postfixMatch = "") {
167
		$query = $this->dbc->prepare('
168
			SELECT `owncloud_name`
169
			FROM `'. $this->getTableName() .'`
170
			WHERE `owncloud_name` LIKE ?
171
		');
172
173
		$res = $query->execute(array($prefixMatch.$this->dbc->escapeLikeParameter($search).$postfixMatch));
174
		$names = array();
175
		if($res !== false) {
176
			while($row = $query->fetch()) {
177
				$names[] = $row['owncloud_name'];
178
			}
179
		}
180
		return $names;
181
	}
182
183
	/**
184
	 * Gets the name based on the provided LDAP UUID.
185
	 * @param string $uuid
186
	 * @return string|false
187
	 */
188
	public function getNameByUUID($uuid) {
189
		return $this->getXbyY('owncloud_name', 'directory_uuid', $uuid);
190
	}
191
192
	/**
193
	 * Gets the UUID based on the provided LDAP DN
194
	 * @param string $dn
195
	 * @return false|string
196
	 * @throws \Exception
197
	 */
198
	public function getUUIDByDN($dn) {
199
		return $this->getXbyY('directory_uuid', 'ldap_dn', $dn);
200
	}
201
202
	/**
203
	 * gets a piece of the mapping list
204
	 * @param int $offset
205
	 * @param int $limit
206
	 * @return array
207
	 */
208
	public function getList($offset = null, $limit = null) {
209
		$query = $this->dbc->prepare('
210
			SELECT
211
				`ldap_dn` AS `dn`,
212
				`owncloud_name` AS `name`,
213
				`directory_uuid` AS `uuid`
214
			FROM `' . $this->getTableName() . '`',
215
			$limit,
216
			$offset
217
		);
218
219
		$query->execute();
220
		return $query->fetchAll();
221
	}
222
223
	/**
224
	 * attempts to map the given entry
225
	 * @param string $fdn fully distinguished name (from LDAP)
226
	 * @param string $name
227
	 * @param string $uuid a unique identifier as used in LDAP
228
	 * @return bool
229
	 */
230
	public function map($fdn, $name, $uuid) {
231 View Code Duplication
		if(mb_strlen($fdn) > 255) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
232
			\OC::$server->getLogger()->error(
233
				'Cannot map, because the DN exceeds 255 characters: {dn}',
234
				[
235
					'app' => 'user_ldap',
236
					'dn' => $fdn,
237
				]
238
			);
239
			return false;
240
		}
241
242
		$row = array(
243
			'ldap_dn'        => $fdn,
244
			'owncloud_name'  => $name,
245
			'directory_uuid' => $uuid
246
		);
247
248
		try {
249
			$result = $this->dbc->insertIfNotExist($this->getTableName(), $row);
250
			// insertIfNotExist returns values as int
251
			return (bool)$result;
252
		} catch (\Exception $e) {
253
			return false;
254
		}
255
	}
256
257
	/**
258
	 * removes a mapping based on the owncloud_name of the entry
259
	 * @param string $name
260
	 * @return bool
261
	 */
262 View Code Duplication
	public function unmap($name) {
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
263
		$query = $this->dbc->prepare('
264
			DELETE FROM `'. $this->getTableName() .'`
265
			WHERE `owncloud_name` = ?');
266
267
		return $this->modify($query, array($name));
268
	}
269
270
	/**
271
	 * Truncate's the mapping table
272
	 * @return bool
273
	 */
274
	public function clear() {
275
		$sql = $this->dbc
276
			->getDatabasePlatform()
277
			->getTruncateTableSQL('`' . $this->getTableName() . '`');
278
		return $this->dbc->prepare($sql)->execute();
279
	}
280
}
281