bfw-systems /
bfw
| 1 | <?php |
||
| 2 | |||
| 3 | namespace BFW\Helpers; |
||
| 4 | |||
| 5 | use \Exception; |
||
| 6 | |||
| 7 | /** |
||
| 8 | * Helpers to securize data |
||
| 9 | */ |
||
| 10 | class Secure |
||
| 11 | { |
||
| 12 | /** |
||
| 13 | * @const ERR_SECURE_KNOWN_TYPE_FILTER_NOT_MANAGED Exception code if the |
||
| 14 | * data type into the method secureKnownTypes() is not managed. |
||
| 15 | */ |
||
| 16 | const ERR_SECURE_KNOWN_TYPE_FILTER_NOT_MANAGED = 1609001; |
||
| 17 | |||
| 18 | /** |
||
| 19 | * @const ERR_SECURE_ARRAY_KEY_NOT_EXIST If the asked key not exist into |
||
| 20 | * the array to secure. |
||
| 21 | */ |
||
| 22 | const ERR_SECURE_ARRAY_KEY_NOT_EXIST = 1609002; |
||
| 23 | |||
| 24 | /** |
||
| 25 | * Hash a string |
||
| 26 | * |
||
| 27 | * @param string $val String to hash |
||
| 28 | * |
||
| 29 | * @return string |
||
| 30 | */ |
||
| 31 | public static function hash(string $val): string |
||
| 32 | { |
||
| 33 | return hash('sha256', md5($val)); |
||
| 34 | } |
||
| 35 | |||
| 36 | /** |
||
| 37 | * Securize a string for some types with filter_var function. |
||
| 38 | * |
||
| 39 | * @param mixed $data String to securize |
||
| 40 | * @param string $type Type of filter |
||
| 41 | * |
||
| 42 | * @return mixed |
||
| 43 | * |
||
| 44 | * @throws \Exception If the type is unknown |
||
| 45 | */ |
||
| 46 | public static function secureKnownType($data, string $type) |
||
| 47 | { |
||
| 48 | $filterType = 'text'; |
||
| 49 | |||
| 50 | if ($type === 'int' || $type === 'integer') { |
||
| 51 | $filterType = FILTER_VALIDATE_INT; |
||
| 52 | } elseif ($type === 'float' || $type === 'double') { |
||
| 53 | $filterType = FILTER_VALIDATE_FLOAT; |
||
| 54 | } elseif ($type === 'bool' || $type === 'boolean') { |
||
| 55 | $filterType = FILTER_VALIDATE_BOOLEAN; |
||
| 56 | } elseif ($type === 'email') { |
||
| 57 | $filterType = FILTER_VALIDATE_EMAIL; |
||
| 58 | } |
||
| 59 | |||
| 60 | if ($filterType === 'text') { |
||
| 61 | throw new Exception( |
||
| 62 | 'Cannot secure the type', |
||
| 63 | self::ERR_SECURE_KNOWN_TYPE_FILTER_NOT_MANAGED |
||
| 64 | ); |
||
| 65 | } |
||
| 66 | |||
| 67 | return filter_var($data, $filterType); |
||
|
0 ignored issues
–
show
Bug
introduced
by
Loading history...
|
|||
| 68 | } |
||
| 69 | |||
| 70 | /** |
||
| 71 | * Securise a mixed data type who are not managed by securiseKnownType. |
||
| 72 | * We work the data like if the type is a string. |
||
| 73 | * |
||
| 74 | * @param mixed $data The variable to securise |
||
| 75 | * @param string $type The type of datas |
||
| 76 | * @param boolean $htmlentities If use htmlentities function |
||
| 77 | * to a better security |
||
| 78 | * |
||
| 79 | * @return mixed |
||
| 80 | */ |
||
| 81 | public static function secureUnknownType( |
||
| 82 | $data, |
||
|
0 ignored issues
–
show
|
|||
| 83 | string $type, |
||
|
0 ignored issues
–
show
|
|||
| 84 | bool $htmlentities |
||
|
0 ignored issues
–
show
|
|||
| 85 | ): string { |
||
| 86 | if ($type !== 'html') { |
||
| 87 | $data = strip_tags($data); |
||
| 88 | } |
||
| 89 | |||
| 90 | if ($type === 'html' || $htmlentities === true) { |
||
| 91 | return htmlentities($data, ENT_QUOTES | ENT_HTML401); |
||
| 92 | } |
||
| 93 | |||
| 94 | return addslashes($data); |
||
| 95 | } |
||
| 96 | |||
| 97 | /** |
||
| 98 | * Securise a variable |
||
| 99 | * |
||
| 100 | * @param mixed $data The variable to securise |
||
| 101 | * @param string $type The type of datas |
||
| 102 | * @param boolean $htmlentities If use htmlentities function |
||
| 103 | * to a better security |
||
| 104 | * |
||
| 105 | * @return mixed |
||
| 106 | * |
||
| 107 | * @throws \Exception If an error with a type of data |
||
| 108 | */ |
||
| 109 | public static function secureData($data, string $type, bool $htmlentities) |
||
| 110 | { |
||
| 111 | $currentClass = get_called_class(); |
||
| 112 | |||
| 113 | if (is_array($data)) { |
||
| 114 | foreach ($data as $key => $val) { |
||
| 115 | unset($data[$key]); |
||
| 116 | |||
| 117 | $key = $currentClass::secureData($key, gettype($key), true); |
||
| 118 | $val = $currentClass::secureData($val, $type, $htmlentities); |
||
| 119 | |||
| 120 | $data[$key] = $val; |
||
| 121 | } |
||
| 122 | |||
| 123 | return $data; |
||
| 124 | } |
||
| 125 | |||
| 126 | try { |
||
| 127 | return $currentClass::secureKnownType($data, $type); |
||
| 128 | } catch (Exception $ex) { |
||
| 129 | if ($ex->getCode() !== self::ERR_SECURE_KNOWN_TYPE_FILTER_NOT_MANAGED) { |
||
| 130 | throw new Exception($ex->getMessage(), $ex->getCode()); |
||
| 131 | } |
||
| 132 | //Else : Use securise like if it's a text type |
||
| 133 | } |
||
| 134 | |||
| 135 | return $currentClass::secureUnknownType($data, $type, $htmlentities); |
||
| 136 | } |
||
| 137 | |||
| 138 | /** |
||
| 139 | * Securise the value of an array key for a declared type. |
||
| 140 | * |
||
| 141 | * @param array &$array The array where is the key |
||
| 142 | * @param string $key The key where is the value to securize |
||
| 143 | * @param string $type The type of data |
||
| 144 | * @param boolean $htmlentities (default: false) If use htmlentities |
||
| 145 | * function to a better security |
||
| 146 | * @param boolean $inline (default: true) If array data are inline |
||
| 147 | * |
||
| 148 | * @return mixed |
||
| 149 | * |
||
| 150 | * @throws \Exception If the key not exist in array |
||
| 151 | */ |
||
| 152 | public static function getSecureKeyInArray( |
||
| 153 | array &$array, |
||
| 154 | string $key, |
||
| 155 | string $type, |
||
| 156 | bool $htmlentities = false, |
||
| 157 | bool $inline = true |
||
| 158 | ) { |
||
| 159 | if (!isset($array[$key])) { |
||
| 160 | throw new Exception( |
||
| 161 | 'The key '.$key.' not exist', |
||
| 162 | self::ERR_SECURE_ARRAY_KEY_NOT_EXIST |
||
| 163 | ); |
||
| 164 | } |
||
| 165 | |||
| 166 | $currentClass = get_called_class(); |
||
| 167 | |||
| 168 | if (!$inline) { |
||
| 169 | //Only space, NUL-byte, and vertical tab. |
||
| 170 | $data = trim($array[$key], ' \0\x0B'); |
||
| 171 | } else { |
||
| 172 | $data = trim($array[$key]); |
||
| 173 | } |
||
| 174 | |||
| 175 | return $currentClass::secureData( |
||
| 176 | $data, |
||
| 177 | $type, |
||
| 178 | $htmlentities |
||
| 179 | ); |
||
| 180 | } |
||
| 181 | |||
| 182 | /** |
||
| 183 | * Obtain many key from an array in one time |
||
| 184 | * |
||
| 185 | * @param array &$arraySrc The source array |
||
| 186 | * @param array $keysList The key list to obtain. |
||
| 187 | * For each item, the key is the name of the key in source array; And the |
||
| 188 | * value the type of the value. The value can also be an object. In this |
||
| 189 | * case, the properties "type" contain the value type, the "htmlenties" |
||
| 190 | * property contain the boolean who indicate if secure system |
||
| 191 | * will use htmlentities, and the "inline" property contain the boolean who |
||
| 192 | * indicate if data are inline |
||
| 193 | * @param boolean $throwOnError (defaut true) If a key not exist, throw an |
||
| 194 | * exception. If false, the value will be null into returned array |
||
| 195 | * |
||
| 196 | * @return array |
||
| 197 | * |
||
| 198 | * @throws \Exception If a key is not found and if $throwOnError is true |
||
| 199 | */ |
||
| 200 | public static function getManySecureKeys( |
||
| 201 | array &$arraySrc, |
||
| 202 | array $keysList, |
||
| 203 | bool $throwOnError = true |
||
| 204 | ): array { |
||
| 205 | $currentClass = get_called_class(); |
||
| 206 | $result = []; |
||
| 207 | |||
| 208 | foreach ($keysList as $keyName => $infos) { |
||
| 209 | if (!is_array($infos)) { |
||
| 210 | $infos = [ |
||
| 211 | 'type' => $infos, |
||
| 212 | 'htmlentities' => false, |
||
| 213 | 'inline' => true |
||
| 214 | ]; |
||
| 215 | } |
||
| 216 | |||
| 217 | try { |
||
| 218 | $result[$keyName] = $currentClass::getSecureKeyInArray( |
||
| 219 | $arraySrc, |
||
| 220 | $keyName, |
||
| 221 | $infos['type'], |
||
| 222 | $infos['htmlentities'], |
||
| 223 | $infos['inline'] |
||
| 224 | ); |
||
| 225 | } catch (Exception $ex) { |
||
| 226 | if ($throwOnError === true) { |
||
| 227 | throw new Exception( |
||
| 228 | 'Error to obtain the key '.$keyName, |
||
| 229 | self::ERR_SECURE_ARRAY_KEY_NOT_EXIST, |
||
| 230 | $ex |
||
| 231 | ); |
||
| 232 | } else { |
||
| 233 | $result[$keyName] = null; |
||
| 234 | } |
||
| 235 | } |
||
| 236 | } |
||
| 237 | |||
| 238 | return $result; |
||
| 239 | } |
||
| 240 | } |
||
| 241 |