Passed
Push — master ( 5c9089...a37889 )
by Georgi
05:25
created

CommonData::validateArrayKeys()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 6
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 3
eloc 3
c 1
b 0
f 0
nc 3
nop 1
dl 0
loc 6
rs 10
1
<?php
2
3
namespace Epesi\Base\CommonData\Database\Models;
4
5
use Kalnoy\Nestedset\NodeTrait;
6
use Illuminate\Database\Eloquent\Model;
7
use Illuminate\Database\Eloquent\Collection;
8
9
class CommonData extends Model {
10
    use NodeTrait;
0 ignored issues
show
Bug introduced by
The trait Kalnoy\Nestedset\NodeTrait requires the property $forceDeleting which is not provided by Epesi\Base\CommonData\Database\Models\CommonData.
Loading history...
11
    
12
    protected $table = 'commondata';
13
    public $timestamps = false;
14
    protected static $unguarded = true;
15
    
16
    public static function getId($path, $clearCache = false)
17
    {
18
    	static $cache;
19
20
    	$parentId = null;
21
    	foreach(explode('/', trim($path,'/')) as $nodeKey) {
22
    		if ($nodeKey === '') continue; //ignore empty paths
23
    		
24
    		if (empty($cache[$parentId][$nodeKey])) {
25
    			if (! $node = self::where('parent_id', $parentId)->where('key', $nodeKey)->first()) {
26
    				return false;
27
    			}
28
29
    			$cache[$parentId][$nodeKey] = $node->id;
30
    		}
31
    		
32
    		$parentId = $id = $cache[$parentId][$nodeKey];
33
    	}
34
    	
35
    	return $id;
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $id does not seem to be defined for all execution paths leading up to this point.
Loading history...
36
    }
37
   
38
    public static function newId($path, $readonly = false)
39
    {
40
    	if (! $path = trim($path,'/')) return false;
41
42
    	$id = $parentId = null;
43
    	foreach(explode('/', $path) as $nodeKey) {
44
    		if ($nodeKey === '') continue;
45
46
    		if (! $node = self::where('parent_id', $parentId)->where('key', $nodeKey)->first()) {
47
    			$node = self::create([
48
    					'parent_id' => $parentId,
49
    					'key' => $nodeKey,
50
    					'readonly' => $readonly,
51
    					'position' => self::where('parent_id', $parentId)->count()
52
    			], $parentId? self::find($parentId): null);
53
    		}
54
    		
55
    		$parentId = $id = $node->id;
56
    	}
57
    	
58
    	return $id;
59
    }
60
    
61
    public static function setValue($path, $value, $overwrite = true, $readonly = false)
62
    {
63
    	if (! $id = self::getId($path)) {
64
    		if (! $id = self::newId($path, $readonly)) return false;
65
    	} else {
66
    		if (! $overwrite) return false;
67
    	}
68
    	
69
    	self::find($id)->update(compact('value', 'readonly'));
70
    	
71
    	return true;
72
    }
73
    
74
    public static function getValue($path, $translate = false)
75
    {
76
    	static $cache;
77
    	
78
    	$key = md5(serialize([$path, $translate]));
79
    	
80
    	if (! isset($cache[$key])) {
81
    		if(! $id = self::getId($path)) return false;
82
83
    		$ret = self::find($id)->value;
84
85
	    	$cache[$key] = $translate? __($ret): $ret;
86
	    }
87
	    
88
	    return $cache[$key];
89
    }
90
    
91
    
92
    /**
93
     * Creates new array for common use.
94
     *
95
     * @param $path string
96
     * @param $array array initialization value
97
     * @param $overwrite bool whether method should overwrite if array already exists, otherwise the data will be appended
98
     * @param $readonly bool do not allow user to change this array from GUI
99
     */
100
    public static function newArray($path, $array, $overwrite = false, $readonly = false)
101
    {
102
    	self::validateArrayKeys($array);
103
    		
104
    	$path = trim($path, '/');
105
    	
106
		if ($id = self::getId($path)) {
107
    		if (! $overwrite) {
108
    			self::extendArray($path, $array);
109
    			return true;
110
    		}
111
    				
112
    		self::find($id)->delete();
113
    	}
114
    			
115
    	if(! $id = self::newId($path, $readonly)) return false;
116
    			
117
    	if ($overwrite) {
118
    		self::find($id)->update(compact('readonly'));
119
    	}
120
    			
121
    	foreach ($array as $key => $value) {
122
    		self::setValue($path . '/' . $key, $value, true, $readonly);
123
    	}
124
    			
125
    	return true;
126
    }
127
128
    /**
129
     * Extends common data array.
130
     *
131
     * @param $path string
132
     * @param $array array values to insert
133
     * @param $overwrite bool whether method should overwrite data if array key already exists, otherwise the data will be preserved
134
     */
135
    public static function extendArray($path, $array, $overwrite=false, $readonly=false)
136
    {
137
    	self::validateArrayKeys($array);
138
    	
139
    	$path = trim($path, '/');
140
    			
141
    	if (! self::getId($path)){
142
    		return self::newArray($path, $array, $overwrite, $readonly);
143
    	}
144
145
    	foreach ($array as $key => $value) {
146
    		self::setValue($path . '/' . $key, $value, $overwrite, $readonly);
147
    	}
148
    }
149
        
150
    /**
151
     * Returns common data array.
152
     *
153
     * @param string array name
154
     * @return mixed returns an array if such array exists, false otherwise
155
     */
156
    public static function getArray($path, $sortColumn = 'position', $silent = false)
157
    {
158
    	return self::getCollection($path, $silent)->sortBy($sortColumn)->pluck('value', 'key')->all();
159
    }
160
161
    /**
162
     * Removes common data array or entry.
163
     *
164
     * @param $path string
165
     * @return true on success, false otherwise
166
     */
167
    public static function deleteArray($path){
168
    	if (! $id = self::getId($path, true)) return false;
0 ignored issues
show
Bug Best Practice introduced by
The expression return false returns the type false which is incompatible with the documented return type true.
Loading history...
169
    	
170
    	self::find($id)->delete();
171
    }
172
173
    /**
174
     * Returns common data collection.
175
     *
176
     * @param $path string
177
     * @return Collection
178
     */
179
    public static function getCollection($path, $silent = false)
180
    {
181
    	static $cache;
182
183
    	if(isset($cache[$path])) {
184
    		return $cache[$path];
185
    	}
186
    	
187
    	if (! $id = self::getId($path)) {
188
    		if ($silent) return collection();
0 ignored issues
show
Bug introduced by
The function collection was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

188
    		if ($silent) return /** @scrutinizer ignore-call */ collection();
Loading history...
189
    		
190
    		new \Exception('Invalid CommonData::getArray() request: ' . $path);
191
    	}
192
    	
193
    	return $cache[$path] = self::where('parent_id', $id)->get();
194
    }
195
    
196
    protected static function validateArrayKeys($array)
197
    {
198
    	foreach($array as $key => $value) {
199
    		if (strpos($key, '/') === false) continue;
200
    		
201
    		\Exception('Invalid common data key: '. $key);
0 ignored issues
show
Bug introduced by
The function Exception was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

201
    		/** @scrutinizer ignore-call */ 
202
      \Exception('Invalid common data key: '. $key);
Loading history...
202
    	}
203
    }
204
}