Anonymization::setModuleName()   A
last analyzed

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 2
dl 0
loc 4
rs 10
c 0
b 0
f 0
cc 1
nc 1
nop 1
1
<?php
2
/**
3
 * Anonymization file.
4
 *
5
 * @package App
6
 *
7
 * @copyright YetiForce S.A.
8
 * @license   YetiForce Public License 6.5 (licenses/LicenseEN.txt or yetiforce.com)
9
 * @author    Mariusz Krzaczkowski <[email protected]>
10
 * @author    Radosław Skrzypczak <[email protected]>
11
 */
12
13
namespace App;
14
15
/**
16
 * Anonymization class.
17
 */
18
class Anonymization
19
{
20
	/** @var int Anonymization logs */
21
	public const LOGS = 0;
22
	/** @var int Anonymization of change history entries on the displayed data layer. */
23
	public const MODTRACKER_DISPLAY = 1;
24
	/** @var int Anonymization of change history entries on the database layer. */
25
	public const MODTRACKER_DB = 2;
26
27
	/**
28
	 * Gets Anonymization types.
29
	 *
30
	 * @return array
31
	 */
32
	public static function getTypes(): array
33
	{
34
		return [
35
			self::LOGS => 'LBL_ANONYMIZATION_LOGS',
36
			self::MODTRACKER_DISPLAY => 'LBL_ANONYMIZATION_MODTRACKER_DISPLAY',
37
			self::MODTRACKER_DB => 'LBL_ANONYMIZATION_MODTRACKER_DB',
38
		];
39
	}
40
41
	/**
42
	 * @var array Word map for anonymization.
43
	 */
44
	const MAPS = [
45
		'password' => ['pass', 'password', 'oldPassword', 'retype_password', 'db_password'],
46
	];
47
	/**
48
	 * @var string Map name
49
	 */
50
	protected $map;
51
	/**
52
	 * @var string Module name
53
	 */
54
	protected $moduleName;
55
	/**
56
	 * @var bool Detect module name if not there
57
	 */
58
	public $detectModuleName = true;
59
	/**
60
	 * @var bool Value for anonymised data
61
	 */
62
	public $value = '****';
63
	/**
64
	 * @var array Data array
65
	 */
66
	protected $data;
67
	/**
68
	 * @var string[] Keys to ananimation
69
	 */
70
	protected $fields;
71
72
	/**
73
	 * Anonymization constructor.
74
	 *
75
	 * @param string $map
76
	 */
77
	public function __construct(string $map = 'all')
78
	{
79
		$this->map = $map;
80
	}
81
82
	/**
83
	 * Set module name.
84
	 *
85
	 * @param string $moduleName
86
	 *
87
	 * @return self
88
	 */
89
	public function setModuleName(string $moduleName): self
90
	{
91
		$this->moduleName = $moduleName;
92
		return $this;
93
	}
94
95
	/**
96
	 * Set data.
97
	 *
98
	 * @param array $data
99
	 *
100
	 * @return self
101
	 */
102
	public function setData(array $data): self
103
	{
104
		$this->data = $data;
105
		return $this;
106
	}
107
108
	/**
109
	 * Get data.
110
	 *
111
	 * @return self
112
	 */
113
	public function getData(): array
114
	{
115
		return $this->data;
0 ignored issues
show
Bug Best Practice introduced by
The expression return $this->data returns the type array which is incompatible with the documented return type App\Anonymization.
Loading history...
116
	}
117
118
	/**
119
	 * Data anonymization.
120
	 *
121
	 * @return void
122
	 */
123
	public function anonymize(): self
124
	{
125
		if (empty($this->data)) {
126
			return $this;
0 ignored issues
show
Bug Best Practice introduced by
The expression return $this returns the type App\Anonymization which is incompatible with the documented return type void.
Loading history...
127
		}
128
		$mapFields = 'all' === $this->map ? self::MAPS : (isset(self::MAPS[$this->map]) ? [$this->map => self::MAPS[$this->map]] : []);
129
		if ($mapFields) {
130
			foreach ($mapFields as $fields) {
131
				$this->fields = $fields;
132
				$this->data = $this->anonymizeByFields($this->data);
133
			}
134
		}
135
		if (('all' === $this->map || 'fields' === $this->map) && (!empty($this->moduleName) || $this->detectModuleName)) {
136
			if (empty($this->moduleName)) {
137
				$this->detectModuleName();
138
			}
139
			if (!empty($this->moduleName) && ($fields = self::getFields(Module::getModuleId($this->moduleName)))) {
140
				$this->fields = $fields;
141
				$this->data = $this->anonymizeByFields($this->data);
142
			}
143
		}
144
		return $this;
0 ignored issues
show
Bug Best Practice introduced by
The expression return $this returns the type App\Anonymization which is incompatible with the documented return type void.
Loading history...
145
	}
146
147
	/**
148
	 * Detect module name.
149
	 *
150
	 * @return void
151
	 */
152
	private function detectModuleName(): void
153
	{
154
		if (!empty($this->data['module'])) {
155
			$this->moduleName = $this->data['module'];
156
		}
157
	}
158
159
	/**
160
	 * Anonymize by fields.
161
	 *
162
	 * @param array $data
163
	 *
164
	 * @return array
165
	 */
166
	private function anonymizeByFields(array $data): array
167
	{
168
		foreach ($data as $key => &$value) {
169
			if (\in_array($key, $this->fields, true)) {
170
				$value = $this->value;
171
			} elseif (\is_array($value)) {
172
				$value = $this->anonymizeByFields($value);
173
			}
174
		}
175
		return $data;
176
	}
177
178
	/**
179
	 * Get list of fields for anonymized.
180
	 *
181
	 * @param int $moduleId Module id
182
	 *
183
	 * @return string[]
184
	 */
185
	public static function getFields(int $moduleId): array
186
	{
187
		if (Cache::has('getFieldsFromRelation', $moduleId)) {
188
			$fields = Cache::get('getFieldsFromRelation', $moduleId);
189
		} else {
190
			$fields = (new \App\Db\Query())->select(['vtiger_field.fieldname'])->from('s_#__fields_anonymization')
191
				->innerJoin('vtiger_field', 'vtiger_field.fieldid = s_#__fields_anonymization.field_id')
192
				->where(['tabid' => $moduleId])
193
				->column();
194
			Cache::save('getFieldsFromRelation', $moduleId, $fields, Cache::LONG);
195
		}
196
		return $fields;
197
	}
198
}
199