Passed
Push — main ( 6d76a8...9a92e8 )
by Jean-Christophe
02:58 queued 15s
created

AclDAOProvider::removePart()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 2
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 2
Bugs 0 Features 1
Metric Value
cc 1
eloc 1
c 2
b 0
f 1
nc 1
nop 1
dl 0
loc 2
ccs 2
cts 2
cp 1
crap 1
rs 10
1
<?php
2
namespace Ubiquity\security\acl\persistence;
3
4
use Ubiquity\cache\CacheManager;
5
use Ubiquity\cache\ClassUtils;
6
use Ubiquity\controllers\Startup;
7
use Ubiquity\db\reverse\DbGenerator;
8
use Ubiquity\exceptions\AclException;
9
use Ubiquity\orm\DAO;
10
use Ubiquity\orm\reverse\DatabaseReversor;
11
use Ubiquity\scaffolding\creators\ClassCreator;
12
use Ubiquity\security\acl\models\AbstractAclPart;
13
use Ubiquity\security\acl\models\AclElement;
14
use Ubiquity\security\acl\models\Permission;
15
use Ubiquity\security\acl\models\Resource;
16
use Ubiquity\security\acl\models\Role;
17
18
/**
19
 * Load and save Acls with a database using DAO.
20
 * Ubiquity\security\acl\persistence$AclDAOProvider
21
 * This class is part of Ubiquity
22
 *
23
 * @author jc
24
 * @version 1.0.2
25
 *
26
 */
27
class AclDAOProvider implements AclProviderInterface {
28
29
	protected string $aclClass;
30
31
	protected string $roleClass;
32
33
	protected string $permissionClass;
34
35
	protected string $resourceClass;
36
37
	/**
38
	 * @param array $config The $config array
39
	 * @param array $classes
40
	 *        	associative array['acl'=>'','role'=>'','resource'=>'','permission'=>'']
41
	 */
42 4
	public function __construct(array &$config,$classes = []) {
43 4
		Startup::$config=$config;
44 4
		$this->aclClass = $classes['acl'] ?? AclElement::class;
45 4
		$this->roleClass = $classes['role'] ?? Role::class;
46 4
		$this->resourceClass = $classes['resource'] ?? Resource::class;
47 4
		$this->permissionClass = $classes['permission'] ?? Permission::class;
48
	}
49
50
	/**
51
	 * Initialize the cache for the ACL models.
52
	 * @param $config
53
	 */
54
	public function initModelsCache(&$config) {
55
		CacheManager::start($config);
56
		CacheManager::createOrmModelCache($this->aclClass);
57
		CacheManager::createOrmModelCache($this->roleClass);
58
		CacheManager::createOrmModelCache($this->resourceClass);
59
		CacheManager::createOrmModelCache($this->permissionClass);
60
	}
61
62
	/**
63
	 * Defines the database offset used for ACL.
64
	 * @param string $dbOffset
65
	 * @param  bool $persist
66
	 */
67
	public function setDbOffset(string $dbOffset = 'default',bool $persist=true):void {
68
		DAO::setModelDatabase($this->aclClass, $dbOffset);
69
		DAO::setModelDatabase($this->resourceClass, $dbOffset);
70
		DAO::setModelDatabase($this->roleClass, $dbOffset);
71
		DAO::setModelDatabase($this->permissionClass, $dbOffset);
72
		if($persist){
73
			CacheManager::storeModelsDatabases(DAO::getModelsDatabase ());
74
		}
75
	}
76
77
	/**
78
	 * Generates the models.
79
	 * @param ?array $classes associative array['acl'=>'','role'=>'','resource'=>'','permission'=>'']
80
	 */
81
	public function createModels(?array $classes=null):void{
82
		$classes??=[
83
			'acl'=>'models\\AclElement','role'=>'models\\Role','resource'=>'models\\Resource','permission'=>'models\\Permission'
84
		];
85
		$this->createModel($classes['acl'] ?? $this->aclClass,AclElement::class);
86
		$this->createModel($classes['role'] ?? $this->roleClass,Role::class);
87
		$this->createModel($classes['resource'] ?? $this->resourceClass,Resource::class);
88
		$this->createModel($classes['permission'] ?? $this->permissionClass,Permission::class);
89
	}
90
91
	public function createModel($modelName,$refName):void{
92
		if($modelName!==$refName){
93
			$className=ClassUtils::getClassSimpleName($modelName);
94
			$ns=ClassUtils::getNamespaceFromCompleteClassname($modelName);
95
			$cCreator=new ClassCreator($className,'',$ns,' extends \\'.$refName);
96
			$cCreator->generate();
97
		}
98
	}
99
100
	/**
101
	 * Generates the tables for ACL model classes.
102
	 * @param string $dbOffset
103
	 * @param bool $createDb
104
	 * @throws AclException
105
	 */
106
	public function generateDbTables(string $dbOffset='default',bool $createDb=false):void{
107
		$this->setDbOffset($dbOffset);
108
		$generator = new DatabaseReversor(new DbGenerator(), $dbOffset);
109
		$activeOffsetValue=DAO::getDbOffset(Startup::$config,$dbOffset);
110
		if(($dbName=$activeOffsetValue['dbName']??'')!='') {
111
			$generator->setModels([$this->aclClass,$this->roleClass,$this->resourceClass,$this->permissionClass]);
112
			$generator->createDatabase($dbName, $createDb);
113
			$db=DAO::getDatabase($dbOffset);
114
			$db->beginTransaction();
115
			$db->execute($generator->__toString());
116
			$db->commit();
117
		}else{
118
			throw new AclException('dbName key is not present or his value is empty!');
119
		}
120
	}
121
122
	/**
123
	 *
124
	 * {@inheritdoc}
125
	 * @see \Ubiquity\security\acl\persistence\AclProviderInterface::loadAllAcls()
126
	 */
127 4
	public function loadAllAcls(): array {
128 4
		$result= DAO::getAll($this->aclClass);
129 4
		foreach ($result as $elm){
130 4
			$elm->setType(AclDAOProvider::class);
131
		}
132 4
		return $result;
133
	}
134
135
	/**
136
	 *
137
	 * {@inheritdoc}
138
	 * @see \Ubiquity\security\acl\persistence\AclProviderInterface::saveAcl()
139
	 */
140 1
	public function saveAcl(AclElement $aclElement) {
141 1
		$aclElement->_rest=[];
1 ignored issue
show
Bug introduced by
The property _rest does not seem to exist on Ubiquity\security\acl\models\AclElement.
Loading history...
142 1
		if(!$this->existPart($aclElement->getResource())){
143
			$this->savePart($aclElement->getResource());
144
		}
145 1
		if(!$this->existPart($aclElement->getPermission())){
146
			$this->savePart($aclElement->getPermission());
147
		}
148 1
		if(!$this->existPart($aclElement->getRole())){
149
			$this->savePart($aclElement->getRole());
150
		}
151 1
		$object = $this->castElement($aclElement);
152 1
		if($this->existAcl($aclElement)){
153
			$res=DAO::update($object);
154
		}else {
155 1
			$res = DAO::insert($object);
156
		}
157 1
		if ($res) {
158 1
			$aclElement->setId($object->getId());
159
		}
160 1
		return $res;
161
	}
162
163
	/**
164
	 *
165
	 * {@inheritdoc}
166
	 * @see \Ubiquity\security\acl\persistence\AclProviderInterface::removeAcl()
167
	 */
168 1
	public function removeAcl(AclElement $aclElement) {
169 1
		return DAO::remove($aclElement);
170
	}
171
172 4
	protected function loadElements(string $className): array {
173 4
		$elements = DAO::getAll($className);
174 4
		$result = [];
175 4
		foreach ($elements as $elm) {
176 4
			$elm->setType(AclDAOProvider::class);
177 4
			$result[$elm->getName()] = $elm;
178
		}
179 4
		return $result;
180
	}
181
182 3
	protected function castElement($part) {
183 3
		$class = $this->getModelClasses()[get_class($part)] ?? get_class($part);
184 3
		return $part->castAs($class);
185
	}
186
187
	/**
188
	 *
189
	 * {@inheritdoc}
190
	 * @see \Ubiquity\security\acl\persistence\AclProviderInterface::loadAllPermissions()
191
	 */
192 4
	public function loadAllPermissions(): array {
193 4
		return $this->loadElements($this->permissionClass);
194
	}
195
196
	/**
197
	 *
198
	 * {@inheritdoc}
199
	 * @see \Ubiquity\security\acl\persistence\AclProviderInterface::loadAllResources()
200
	 */
201 4
	public function loadAllResources(): array {
202 4
		return $this->loadElements($this->resourceClass);
203
	}
204
205
	/**
206
	 *
207
	 * {@inheritdoc}
208
	 * @see \Ubiquity\security\acl\persistence\AclProviderInterface::loadAllRoles()
209
	 */
210 4
	public function loadAllRoles(): array {
211 4
		return $this->loadElements($this->roleClass);
212
	}
213
214
	/**
215
	 *
216
	 * {@inheritdoc}
217
	 * @see \Ubiquity\security\acl\persistence\AclProviderInterface::savePart()
218
	 */
219 2
	public function savePart(\Ubiquity\security\acl\models\AbstractAclPart $part) {
220 2
		$object = $this->castElement($part);
221 2
		if($this->existPart($part)) {
222
			$object->_rest=[];
223
			$res = DAO::update($object);
224
		}else{
225 2
			$res=DAO::insert($object);
226
		}
227 2
		if ($res) {
228 2
			$part->setName($object->getName());
229
		}
230 2
		return $res;
231
	}
232
233
	/**
234
	 *
235
	 * {@inheritdoc}
236
	 * @see \Ubiquity\security\acl\persistence\AclProviderInterface::updatePart()
237
	 */
238 1
	public function updatePart(string $id,\Ubiquity\security\acl\models\AbstractAclPart $part) {
239 1
		$object=$this->castElement($part);
240 1
		$object->_rest=[];
241 1
		$object->_pkv['___name']=$id;
242 1
		return DAO::update($object);
243
	}
244
245
	/**
246
	 *
247
	 * {@inheritdoc}
248
	 * @see \Ubiquity\security\acl\persistence\AclProviderInterface::removePart()
249
	 */
250 2
	public function removePart(\Ubiquity\security\acl\models\AbstractAclPart $part) {
251 2
		return DAO::remove($this->castElement($part));
252
	}
253
254 1
	public function isAutosave(): bool {
255 1
		return true;
256
	}
257
258
	public function saveAll(): void {}
259
260 3
	public function existPart(AbstractAclPart $part): bool {
261 3
		$elm = $this->castElement($part);
262 3
		return DAO::exists(\get_class($elm), 'name= ?', [
263 3
			$elm->getName()
264 3
		]);
265
	}
266
267 1
	public function existAcl(AclElement $aclElement): bool {
268 1
		$elm = $this->castElement($aclElement);
269 1
		return DAO::exists(\get_class($elm), 'id= ?', [
270 1
			$elm->getId()
271 1
		]);
272
	}
273
274
	public function getDetails(): array {
275
		return [
276
			'user' => $this->roleClass,
277
			'archive' => $this->resourceClass,
278
			'unlock alternate' => $this->permissionClass,
279
			'lock' => $this->aclClass
280
		];
281
	}
282
283
	public function getModelClassesSwap(): array {
284
		$swap = $this->getModelClasses();
285
		$classes = \array_values($swap);
286
		$result = [];
287
		foreach ($classes as $class) {
288
			$result[$class] = $swap;
289
		}
290
		return $result;
291
	}
292
293 3
	public function getModelClasses(): array {
294 3
		return [
295 3
			AclElement::class => $this->aclClass,
296 3
			Role::class => $this->roleClass,
297 3
			Resource::class => $this->resourceClass,
298 3
			Permission::class => $this->permissionClass
299 3
		];
300
	}
301
302
	public function clearAll(): void {}
303
304
	/**
305
	 * Initializes AclDAOProvider and creates ACL tables in the specified dbOffset.
306
	 * Do not use in production
307
	 *
308
	 * @param array $config
309
	 * @param string $dbOffset
310
	 * @param array $classes
311
	 *        	associative array['acl'=>'','role'=>'','resource'=>'','permission'=>'']
312
	 * @return AclDAOProvider
313
	 * @throws AclException
314
	 */
315
	public static function initializeProvider(array $config,string $dbOffset='default',array $classes = []): AclDAOProvider {
316
		$dbProvider=new AclDAOProvider($config,$classes);
317
		$dbProvider->initModelsCache($config);
318
		$dbProvider->setDbOffset($dbOffset);
319
		$dbProvider->generateDbTables($dbOffset);
320
		return $dbProvider;
321
	}
322
}
323