mirror of
https://git.imnavajas.es/jjimenez/safekat.git
synced 2025-07-25 22:52:08 +00:00
Eliminados modelos y su tabla del webguard
This commit is contained in:
@ -1,273 +0,0 @@
|
||||
<?php
|
||||
|
||||
namespace App\Controllers;
|
||||
|
||||
use App\Libraries\PasswordHash;
|
||||
use App\Models\SettingsModel;
|
||||
use App\Models\Usuarios\UserModel;
|
||||
use CodeIgniter\HTTP\IncomingRequest;
|
||||
use CodeIgniter\HTTP\ResponseInterface;
|
||||
use CodeIgniter\RESTful\ResourceController;
|
||||
use CodeIgniter\Validation\Exceptions\ValidationException;
|
||||
use Config\Services;
|
||||
|
||||
class Api extends ResourceController
|
||||
{
|
||||
private $user_model;
|
||||
private $settings_model;
|
||||
private $data_format;
|
||||
|
||||
function __construct()
|
||||
{
|
||||
$this->user_model = new UserModel();
|
||||
$this->settings_model = new SettingsModel();
|
||||
$this->data_format = getenv('api.return')??'json';
|
||||
}
|
||||
|
||||
public function index()
|
||||
{
|
||||
return $this->response->setJSON([
|
||||
'message' => 'Welcome!'
|
||||
]);
|
||||
}
|
||||
|
||||
public function status()
|
||||
{
|
||||
return $this->response->setJSON([
|
||||
'status' => true,
|
||||
'message' => 'The system is running!'
|
||||
]);
|
||||
}
|
||||
|
||||
public function signIn()
|
||||
{
|
||||
$rules = [
|
||||
'email' => 'required|valid_email|validateAuthPermission[email]',
|
||||
'password' => 'required|validateAuthPassword[email, password]'
|
||||
];
|
||||
$errors = [
|
||||
'email' => [
|
||||
'required' => 'The email field is required.',
|
||||
'valid_email' => 'Invalid email.',
|
||||
'validateAuthPermission' => 'This user {value} does not have access permission.'
|
||||
],
|
||||
'password' => [
|
||||
'required' => 'The password field is required.',
|
||||
'validateAuthPassword' => 'Invalid password.'
|
||||
]
|
||||
];
|
||||
$input = $this->baseRequest($this->request);
|
||||
if (!$this->baseValidateRequest($input, $rules, $errors)) {
|
||||
return $this->baseResponse($this->validator->getErrors(),ResponseInterface::HTTP_BAD_REQUEST);
|
||||
}
|
||||
return $this->generateCredential($input['email']);
|
||||
}
|
||||
|
||||
private function generateCredential(string $email, int $responseCode = ResponseInterface::HTTP_OK){
|
||||
try {
|
||||
helper('jwt');
|
||||
return $this->baseResponse([
|
||||
'access_token' => jwtSignature($email)
|
||||
]);
|
||||
} catch (\Exception $exception) {
|
||||
return $this->baseResponse(['error' => $exception->getMessage()], $responseCode);
|
||||
}
|
||||
}
|
||||
|
||||
private function baseResponse(array $responseBody, int $code = ResponseInterface::HTTP_OK)
|
||||
{
|
||||
if($this->data_format == 'json'){
|
||||
return $this->response->setStatusCode($code)->setJSON($responseBody)??'';
|
||||
}else{
|
||||
return $this->response->setStatusCode($code)->setXML($responseBody)??'';
|
||||
}
|
||||
}
|
||||
|
||||
private function baseRequest(IncomingRequest $request){
|
||||
return $request->getVar()??[];
|
||||
}
|
||||
|
||||
private function baseValidateRequest(array $input, array $rules, array $messages = []){
|
||||
$this->validator = Services::Validation()->setRules($rules);
|
||||
if (is_string($rules)) {
|
||||
$validation = config('Validation');
|
||||
if (!isset($validation->$rules)) {
|
||||
throw ValidationException::forRuleNotFound($rules);
|
||||
}
|
||||
if (!$messages) {
|
||||
$errorName = $rules . '_errors';
|
||||
$messages = $validation->$errorName ?? [];
|
||||
}
|
||||
$rules = $validation->$rules;
|
||||
}
|
||||
return $this->validator->setRules($rules, $messages)->run($input);
|
||||
}
|
||||
|
||||
public function user($method = null, $key = null)
|
||||
{
|
||||
switch ($method):
|
||||
/**
|
||||
* Return all users.
|
||||
*/
|
||||
case 'all':
|
||||
try {
|
||||
$data = $this->user_model->select('token,first_name,last_name,date_birth,email,mobile,picture,language,address,address,state,country,zip_code,status,created_at,updated_at')->findAll()??[];
|
||||
return $this->setResponseFormat($this->data_format)->respond($data);
|
||||
} catch (\Exception $exception) {
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => $exception->getMessage()
|
||||
]);
|
||||
}
|
||||
/**
|
||||
* Return user for token id.
|
||||
*/
|
||||
case 'id':
|
||||
try {
|
||||
$data = $this->user_model->select('token,first_name,last_name,date_birth,email,mobile,picture,language,address,address,state,country,zip_code,status,created_at,updated_at')->where('token',$key)->first()??[];
|
||||
return $this->setResponseFormat($this->data_format)->respond($data);
|
||||
} catch (\Exception $exception) {
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => $exception->getMessage()
|
||||
]);
|
||||
}
|
||||
/**
|
||||
* Return add user.
|
||||
*/
|
||||
case 'add':
|
||||
try {
|
||||
$body = $this->request->getVar() == [] ? (array) $this->request->getJSON() : $this->request->getVar();
|
||||
if(empty($body["first_name"]??"")){
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => 'The first name parameter is null or empty.'
|
||||
]);
|
||||
}
|
||||
if(empty($body["last_name"]??"")){
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => 'The last name parameter is null or empty.'
|
||||
]);
|
||||
}
|
||||
if(empty($body["email"]??"")){
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => 'The email parameter is null or empty.'
|
||||
]);
|
||||
}else{
|
||||
$validate = $this->user_model->where('email',$body["email"]??"")->countAllResults();
|
||||
if($validate > 0){
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => 'Email already registered!'
|
||||
]);
|
||||
}
|
||||
}
|
||||
if(empty($body["password"]??"")){
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => 'The password parameter is null or empty.'
|
||||
]);
|
||||
}else{
|
||||
if(strlen($body["password"]??"") < 8){
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => 'Password must be at least 8 characters long.'
|
||||
]);
|
||||
}
|
||||
}
|
||||
$settings = $this->settings_model->first()??[];
|
||||
$phpass = new PasswordHash(8, true);
|
||||
$token = md5(uniqid(rand(), true));
|
||||
$this->user_model->save([
|
||||
'group' => $settings['default_role'],
|
||||
'first_name' => $body['first_name'],
|
||||
'last_name' => $body['last_name'],
|
||||
'mobile' => '',
|
||||
'picture' => '/assets/img/default-user.png',
|
||||
'email' => $body['email'],
|
||||
'password' => $phpass->HashPassword($body['password']),
|
||||
'last_access' => date('Y-m-d h:i:s'),
|
||||
'last_ip' => '::1',
|
||||
'language' => $settings['default_language'],
|
||||
'token' => $token,
|
||||
'status' => true
|
||||
]);
|
||||
$data = $this->user_model->select('token,first_name,last_name,date_birth,email,mobile,picture,language,address,address,state,country,zip_code,status,created_at,updated_at')->where('token',$token)->first()??[];
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => false,
|
||||
'message' => 'Added successfully!',
|
||||
'data' => $data??[]
|
||||
]);
|
||||
} catch (\Exception $exception) {
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => $exception->getMessage()
|
||||
]);
|
||||
}
|
||||
/**
|
||||
* Return edit user.
|
||||
*/
|
||||
case 'edit':
|
||||
try {
|
||||
$data = $this->user_model->where('token',$key)->first()??[];
|
||||
if($data == []){
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => 'User not found!'
|
||||
]);
|
||||
}
|
||||
$body = $this->request->getVar() == [] ? (array) $this->request->getJSON() : $this->request->getVar();
|
||||
$this->user_model->save([
|
||||
'id_user' => $data['id_user'],
|
||||
'first_name' => empty($body["first_name"]??"")?$data['first_name']:$body["first_name"]??"",
|
||||
'last_name' => empty($body["last_name"]??"")?$data['last_name']:$body["last_name"]??"",
|
||||
'date_birth' => empty($body["date_birth"]??"")?$data['date_birth']:$body["date_birth"]??"",
|
||||
'address' => empty($body["address"]??"")?$data['address']:$body["address"]??"",
|
||||
'city' => empty($body["city"]??"")?$data['city']:$body["city"]??"",
|
||||
'state' => empty($body["state"]??"")?$data['state']:$body["state"]??"",
|
||||
'country' => empty($body["country"]??"")?$data['country']:$body["country"]??"",
|
||||
'zip_code' => empty($body["zip_code"]??"")?$data['zip_code']:$body["zip_code"]??"",
|
||||
'mobile' => empty($body["mobile"]??"")?$data['mobile']:$body["mobile"]??"",
|
||||
'status' => empty($body["status"]??"")?$data['status']:$body["status"]??""
|
||||
]);
|
||||
$data = $this->user_model->select('token,first_name,last_name,date_birth,email,mobile,picture,language,address,address,state,country,zip_code,status,created_at,updated_at')->where('token',$key)->first()??[];
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => false,
|
||||
'message' => 'Successfully Edited!',
|
||||
'data' => $data??[]
|
||||
]);
|
||||
} catch (\Exception $exception) {
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => $exception->getMessage()
|
||||
]);
|
||||
}
|
||||
/**
|
||||
* Return delete user.
|
||||
*/
|
||||
case 'delete':
|
||||
try {
|
||||
$this->user_model->where('token', $key)->delete();
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => false,
|
||||
'message' => 'Successfully deleted!'
|
||||
]);
|
||||
} catch (\Exception $exception) {
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => $exception->getMessage()
|
||||
]);
|
||||
}
|
||||
/**
|
||||
* Return Default.
|
||||
*/
|
||||
default:
|
||||
return $this->setResponseFormat($this->data_format)->respond([
|
||||
'error' => true,
|
||||
'message' => 'Method call is invalid.'
|
||||
]);
|
||||
endswitch;
|
||||
}
|
||||
}
|
||||
@ -1,59 +0,0 @@
|
||||
<?php
|
||||
|
||||
use App\Models\SettingsModel;
|
||||
use App\Models\Usuarios\UserModel;
|
||||
use Firebase\JWT\JWT;
|
||||
|
||||
/**
|
||||
* Receives JWT authentication header and returns a string.
|
||||
* @access public
|
||||
* @param string $authHeader
|
||||
* @return string
|
||||
*/
|
||||
if(!function_exists('jwtRequest')) {
|
||||
function jwtRequest($authHeader){
|
||||
if (is_null($authHeader)) {
|
||||
throw new Exception('Missing or invalid jwt access token.');
|
||||
}
|
||||
return explode(' ', $authHeader)[1];
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Validates the token by decrypting and checking the database.
|
||||
* @access public
|
||||
* @param string $token
|
||||
* @return array
|
||||
*/
|
||||
if(!function_exists('jwtValidateRequest')) {
|
||||
function jwtValidateRequest(string $token)
|
||||
{
|
||||
$settingsBase = new SettingsModel();
|
||||
$settings = $settingsBase->first()??[];
|
||||
$decode = JWT::decode($token, $settings['jwt_private_key']??'', ['HS256']);
|
||||
$userModel = new UserModel();
|
||||
return $userModel->where('email', $decode->email)->first();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Signs a new token.
|
||||
* @access public
|
||||
* @param string $email
|
||||
* @return string
|
||||
*/
|
||||
if(!function_exists('jwtSignature')) {
|
||||
function jwtSignature(string $email)
|
||||
{
|
||||
$settingsBase = new SettingsModel();
|
||||
$settings = $settingsBase->first()??[];
|
||||
$time = time();
|
||||
$expiration = $time + (intval($settings['jwt_token_lifetime']??0) * 60);
|
||||
$payload = [
|
||||
'email' => $email,
|
||||
'iat' => $time,
|
||||
'exp' => $expiration,
|
||||
];
|
||||
return JWT::encode($payload, $settings['jwt_private_key']??'');
|
||||
}
|
||||
}
|
||||
@ -1,160 +0,0 @@
|
||||
<?php namespace App\Libraries;
|
||||
|
||||
class Authenticator {
|
||||
protected $codeLength = 6;
|
||||
|
||||
public function createSecret($secretLength = 16) {
|
||||
$validChars = $this->Base32T();
|
||||
if ($secretLength < 16 || $secretLength > 128) {
|
||||
throw new Exception('Bad secret length');
|
||||
}
|
||||
$secret = '';
|
||||
$rnd = false;
|
||||
if (function_exists('random_bytes')) {
|
||||
$rnd = random_bytes($secretLength);
|
||||
} elseif (function_exists('mcrypt_create_iv')) {
|
||||
$rnd = mcrypt_create_iv($secretLength, MCRYPT_DEV_URANDOM);
|
||||
} elseif (function_exists('openssl_random_pseudo_bytes')) {
|
||||
$rnd = openssl_random_pseudo_bytes($secretLength, $cryptoStrong);
|
||||
if (!$cryptoStrong) {
|
||||
$rnd = false;
|
||||
}
|
||||
}
|
||||
if ($rnd !== false) {
|
||||
for ($i = 0; $i < $secretLength; ++$i) {
|
||||
$secret .= $validChars[ord($rnd[$i]) & 31];
|
||||
}
|
||||
} else {
|
||||
throw new Exception('No source of secure random');
|
||||
}
|
||||
|
||||
return $secret;
|
||||
}
|
||||
|
||||
|
||||
public function getCode($secret, $timeSlice = null) {
|
||||
if ($timeSlice === null) {
|
||||
$timeSlice = floor(time() / 30);
|
||||
}
|
||||
|
||||
$secretkey = $this->decode($secret);
|
||||
|
||||
$time = chr(0).chr(0).chr(0).chr(0).pack('N*', $timeSlice);
|
||||
$hm = hash_hmac('SHA1', $time, $secretkey, true);
|
||||
$offset = ord(substr($hm, -1)) & 0x0F;
|
||||
$hashpart = substr($hm, $offset, 4);
|
||||
$value = unpack('N', $hashpart);
|
||||
$value = $value[1];
|
||||
$value = $value & 0x7FFFFFFF;
|
||||
$modulo = pow(10, $this->codeLength);
|
||||
return str_pad($value % $modulo, $this->codeLength, '0', STR_PAD_LEFT);
|
||||
}
|
||||
|
||||
public function GetQR($name, $secret, $title = null, $params = array()) {
|
||||
$width = !empty($params['width']) && (int) $params['width'] > 0 ? (int) $params['width'] : 160;
|
||||
$height = !empty($params['height']) && (int) $params['height'] > 0 ? (int) $params['height'] : 160;
|
||||
$level = !empty($params['level']) && array_search($params['level'], array('L', 'M', 'Q', 'H')) !== false ? $params['level'] : 'M';
|
||||
|
||||
$urlencoded = urlencode('otpauth://totp/'.$name.'?secret='.$secret.'');
|
||||
if (isset($title)) {
|
||||
$urlencoded .= urlencode('&issuer='.urlencode($title));
|
||||
}
|
||||
|
||||
return "https://api.qrserver.com/v1/create-qr-code/?data=$urlencoded&size=${width}x${height}&ecc=$level";
|
||||
}
|
||||
|
||||
public function verify($secret, $code, $discrepancy = 1, $currentTimeSlice = null) {
|
||||
if ($currentTimeSlice === null) {
|
||||
$currentTimeSlice = floor(time() / 30);
|
||||
}
|
||||
|
||||
if (strlen($code) != 6) {
|
||||
return false;
|
||||
}
|
||||
|
||||
for ($i = -$discrepancy; $i <= $discrepancy; ++$i) {
|
||||
$calculatedCode = $this->getCode($secret, $currentTimeSlice + $i);
|
||||
if ($this->timingSafeEquals($calculatedCode, $code)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
public function setCodeLength($length) {
|
||||
$this->codeLength = $length;
|
||||
return $this;
|
||||
}
|
||||
|
||||
protected function decode($secret) {
|
||||
if (empty($secret)) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$base32chars = $this->Base32T();
|
||||
$base32charsFlipped = array_flip($base32chars);
|
||||
|
||||
$paddingCharCount = substr_count($secret, $base32chars[32]);
|
||||
$allowedValues = array(6, 4, 3, 1, 0);
|
||||
if (!in_array($paddingCharCount, $allowedValues)) {
|
||||
return false;
|
||||
}
|
||||
for ($i = 0; $i < 4; ++$i) {
|
||||
if ($paddingCharCount == $allowedValues[$i] &&
|
||||
substr($secret, -($allowedValues[$i])) != str_repeat($base32chars[32], $allowedValues[$i])) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
$secret = str_replace('=', '', $secret);
|
||||
$secret = str_split($secret);
|
||||
$binaryString = '';
|
||||
for ($i = 0; $i < count($secret); $i = $i + 8) {
|
||||
$x = '';
|
||||
if (!in_array($secret[$i], $base32chars)) {
|
||||
return false;
|
||||
}
|
||||
for ($j = 0; $j < 8; ++$j) {
|
||||
$x .= str_pad(base_convert(@$base32charsFlipped[@$secret[$i + $j]], 10, 2), 5, '0', STR_PAD_LEFT);
|
||||
}
|
||||
$eightBits = str_split($x, 8);
|
||||
for ($z = 0; $z < count($eightBits); ++$z) {
|
||||
$binaryString .= (($y = chr(base_convert($eightBits[$z], 2, 10))) || ord($y) == 48) ? $y : '';
|
||||
}
|
||||
}
|
||||
|
||||
return $binaryString;
|
||||
}
|
||||
|
||||
protected function Base32T() {
|
||||
return array(
|
||||
'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', // 7
|
||||
'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', // 15
|
||||
'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', // 23
|
||||
'Y', 'Z', '2', '3', '4', '5', '6', '7', // 31
|
||||
'=', // padding char
|
||||
);
|
||||
}
|
||||
|
||||
private function timingSafeEquals($safeString, $userString) {
|
||||
if (function_exists('hash_equals')) {
|
||||
return hash_equals($safeString, $userString);
|
||||
}
|
||||
$safeLen = strlen($safeString);
|
||||
$userLen = strlen($userString);
|
||||
|
||||
if ($userLen != $safeLen) {
|
||||
return false;
|
||||
}
|
||||
|
||||
$result = 0;
|
||||
|
||||
for ($i = 0; $i < $userLen; ++$i) {
|
||||
$result |= (ord($safeString[$i]) ^ ord($userString[$i]));
|
||||
}
|
||||
|
||||
// They are only identical strings if $result is exactly 0...
|
||||
return $result === 0;
|
||||
}
|
||||
}
|
||||
@ -1,227 +0,0 @@
|
||||
<?php namespace App\Libraries;
|
||||
#
|
||||
# Portable PHP password hashing framework.
|
||||
#
|
||||
# Version 0.5 / genuine.
|
||||
#
|
||||
# Written by Solar Designer <solar at openwall.com> in 2004-2006 and placed in
|
||||
# the public domain. Revised in subsequent years, still public domain.
|
||||
#
|
||||
# There's absolutely no warranty.
|
||||
#
|
||||
# The homepage URL for this framework is:
|
||||
#
|
||||
# http://www.openwall.com/phpass/
|
||||
#
|
||||
# Please be sure to update the Version line if you edit this file in any way.
|
||||
# It is suggested that you leave the main version number intact, but indicate
|
||||
# your project name (after the slash) and add your own revision information.
|
||||
#
|
||||
# Please do not change the "private" password hashing method implemented in
|
||||
# here, thereby making your hashes incompatible. However, if you must, please
|
||||
# change the hash type identifier (the "$P$") to something different.
|
||||
#
|
||||
# Obviously, since this code is in the public domain, the above are not
|
||||
# requirements (there can be none), but merely suggestions.
|
||||
#
|
||||
class PasswordHash {
|
||||
var $itoa64;
|
||||
var $iteration_count_log2;
|
||||
var $portable_hashes;
|
||||
var $random_state;
|
||||
|
||||
function __construct($iteration_count_log2, $portable_hashes)
|
||||
{
|
||||
$this->itoa64 = './0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz';
|
||||
|
||||
if ($iteration_count_log2 < 4 || $iteration_count_log2 > 31)
|
||||
$iteration_count_log2 = 8;
|
||||
$this->iteration_count_log2 = $iteration_count_log2;
|
||||
|
||||
$this->portable_hashes = $portable_hashes;
|
||||
|
||||
$this->random_state = microtime();
|
||||
if (function_exists('getmypid'))
|
||||
$this->random_state .= getmypid();
|
||||
}
|
||||
|
||||
function PasswordHash($iteration_count_log2, $portable_hashes)
|
||||
{
|
||||
self::__construct($iteration_count_log2, $portable_hashes);
|
||||
}
|
||||
|
||||
function get_random_bytes($count)
|
||||
{
|
||||
$output = '';
|
||||
if (@is_readable('/dev/urandom') &&
|
||||
($fh = @fopen('/dev/urandom', 'rb'))) {
|
||||
$output = fread($fh, $count);
|
||||
fclose($fh);
|
||||
}
|
||||
|
||||
if (strlen($output) < $count) {
|
||||
$output = '';
|
||||
for ($i = 0; $i < $count; $i += 16) {
|
||||
$this->random_state =
|
||||
md5(microtime() . $this->random_state);
|
||||
$output .= md5($this->random_state, TRUE);
|
||||
}
|
||||
$output = substr($output, 0, $count);
|
||||
}
|
||||
|
||||
return $output;
|
||||
}
|
||||
|
||||
function encode64($input, $count)
|
||||
{
|
||||
$output = '';
|
||||
$i = 0;
|
||||
do {
|
||||
$value = ord($input[$i++]);
|
||||
$output .= $this->itoa64[$value & 0x3f];
|
||||
if ($i < $count)
|
||||
$value |= ord($input[$i]) << 8;
|
||||
$output .= $this->itoa64[($value >> 6) & 0x3f];
|
||||
if ($i++ >= $count)
|
||||
break;
|
||||
if ($i < $count)
|
||||
$value |= ord($input[$i]) << 16;
|
||||
$output .= $this->itoa64[($value >> 12) & 0x3f];
|
||||
if ($i++ >= $count)
|
||||
break;
|
||||
$output .= $this->itoa64[($value >> 18) & 0x3f];
|
||||
} while ($i < $count);
|
||||
|
||||
return $output;
|
||||
}
|
||||
|
||||
function gensalt_private($input)
|
||||
{
|
||||
$output = '$P$';
|
||||
$output .= $this->itoa64[min($this->iteration_count_log2 +
|
||||
((PHP_VERSION >= '5') ? 5 : 3), 30)];
|
||||
$output .= $this->encode64($input, 6);
|
||||
|
||||
return $output;
|
||||
}
|
||||
|
||||
function crypt_private($password, $setting)
|
||||
{
|
||||
$output = '*0';
|
||||
if (substr($setting, 0, 2) === $output)
|
||||
$output = '*1';
|
||||
|
||||
$id = substr($setting, 0, 3);
|
||||
# We use "$P$", phpBB3 uses "$H$" for the same thing
|
||||
if ($id !== '$P$' && $id !== '$H$')
|
||||
return $output;
|
||||
|
||||
$count_log2 = strpos($this->itoa64, $setting[3]);
|
||||
if ($count_log2 < 7 || $count_log2 > 30)
|
||||
return $output;
|
||||
|
||||
$count = 1 << $count_log2;
|
||||
|
||||
$salt = substr($setting, 4, 8);
|
||||
if (strlen($salt) !== 8)
|
||||
return $output;
|
||||
|
||||
# We were kind of forced to use MD5 here since it's the only
|
||||
# cryptographic primitive that was available in all versions
|
||||
# of PHP in use. To implement our own low-level crypto in PHP
|
||||
# would have resulted in much worse performance and
|
||||
# consequently in lower iteration counts and hashes that are
|
||||
# quicker to crack (by non-PHP code).
|
||||
$hash = md5($salt . $password, TRUE);
|
||||
do {
|
||||
$hash = md5($hash . $password, TRUE);
|
||||
} while (--$count);
|
||||
|
||||
$output = substr($setting, 0, 12);
|
||||
$output .= $this->encode64($hash, 16);
|
||||
|
||||
return $output;
|
||||
}
|
||||
|
||||
function gensalt_blowfish($input)
|
||||
{
|
||||
# This one needs to use a different order of characters and a
|
||||
# different encoding scheme from the one in encode64() above.
|
||||
# We care because the last character in our encoded string will
|
||||
# only represent 2 bits. While two known implementations of
|
||||
# bcrypt will happily accept and correct a salt string which
|
||||
# has the 4 unused bits set to non-zero, we do not want to take
|
||||
# chances and we also do not want to waste an additional byte
|
||||
# of entropy.
|
||||
$itoa64 = './ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
|
||||
|
||||
$output = '$2a$';
|
||||
$output .= chr(ord('0') + $this->iteration_count_log2 / 10);
|
||||
$output .= chr(ord('0') + $this->iteration_count_log2 % 10);
|
||||
$output .= '$';
|
||||
|
||||
$i = 0;
|
||||
do {
|
||||
$c1 = ord($input[$i++]);
|
||||
$output .= $itoa64[$c1 >> 2];
|
||||
$c1 = ($c1 & 0x03) << 4;
|
||||
if ($i >= 16) {
|
||||
$output .= $itoa64[$c1];
|
||||
break;
|
||||
}
|
||||
|
||||
$c2 = ord($input[$i++]);
|
||||
$c1 |= $c2 >> 4;
|
||||
$output .= $itoa64[$c1];
|
||||
$c1 = ($c2 & 0x0f) << 2;
|
||||
|
||||
$c2 = ord($input[$i++]);
|
||||
$c1 |= $c2 >> 6;
|
||||
$output .= $itoa64[$c1];
|
||||
$output .= $itoa64[$c2 & 0x3f];
|
||||
} while (1);
|
||||
|
||||
return $output;
|
||||
}
|
||||
|
||||
function HashPassword($password)
|
||||
{
|
||||
$random = '';
|
||||
|
||||
if (CRYPT_BLOWFISH === 1 && !$this->portable_hashes) {
|
||||
$random = $this->get_random_bytes(16);
|
||||
$hash =
|
||||
crypt($password, $this->gensalt_blowfish($random));
|
||||
if (strlen($hash) === 60)
|
||||
return $hash;
|
||||
}
|
||||
|
||||
if (strlen($random) < 6)
|
||||
$random = $this->get_random_bytes(6);
|
||||
$hash =
|
||||
$this->crypt_private($password,
|
||||
$this->gensalt_private($random));
|
||||
if (strlen($hash) === 34)
|
||||
return $hash;
|
||||
|
||||
# Returning '*' on error is safe here, but would _not_ be safe
|
||||
# in a crypt(3)-like function used _both_ for generating new
|
||||
# hashes and for validating passwords against existing hashes.
|
||||
return '*';
|
||||
}
|
||||
|
||||
function CheckPassword($password, $stored_hash)
|
||||
{
|
||||
$hash = $this->crypt_private($password, $stored_hash);
|
||||
if ($hash[0] === '*')
|
||||
$hash = crypt($password, $stored_hash);
|
||||
|
||||
# This is not constant-time. In order to keep the code simple,
|
||||
# for timing safety we currently rely on the salts being
|
||||
# unpredictable, which they are at least in the non-fallback
|
||||
# cases (that is, when we use /dev/urandom and bcrypt).
|
||||
return $hash === $stored_hash;
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
||||
@ -1,13 +0,0 @@
|
||||
<?php
|
||||
namespace App\Models;
|
||||
|
||||
class CurrencyModel extends BaseModel
|
||||
{
|
||||
protected $table = 'auth_currency';
|
||||
protected $primaryKey = 'id_currency';
|
||||
protected $allowedFields = [
|
||||
'code',
|
||||
'name',
|
||||
'data_lang'
|
||||
];
|
||||
}
|
||||
@ -1,21 +0,0 @@
|
||||
<?php
|
||||
namespace App\Models;
|
||||
|
||||
class NotificationModel extends BaseModel
|
||||
{
|
||||
protected $table = 'auth_notification';
|
||||
protected $primaryKey = 'id_notification';
|
||||
protected $allowedFields = [
|
||||
'user_sender',
|
||||
'user_recipient',
|
||||
'title',
|
||||
'body',
|
||||
'is_read',
|
||||
'is_send_email',
|
||||
'send_email_notification',
|
||||
'token'
|
||||
];
|
||||
protected $useTimestamps = true;
|
||||
protected $createdField = 'created_at';
|
||||
protected $updatedField = 'updated_at';
|
||||
}
|
||||
@ -1,17 +0,0 @@
|
||||
<?php
|
||||
|
||||
namespace App\Models;
|
||||
|
||||
class PasswordRecoveryModel extends BaseModel
|
||||
{
|
||||
protected $table = 'auth_password_recovery';
|
||||
protected $primaryKey = 'id_pass_recovery';
|
||||
protected $allowedFields = [
|
||||
'user',
|
||||
'token',
|
||||
'changed'
|
||||
];
|
||||
protected $useTimestamps = true;
|
||||
protected $createdField = 'created_at';
|
||||
protected $updatedField = 'updated_at';
|
||||
}
|
||||
@ -1,16 +0,0 @@
|
||||
<?php
|
||||
namespace App\Models;
|
||||
|
||||
class TemplateModel extends BaseModel
|
||||
{
|
||||
protected $table = 'auth_template';
|
||||
protected $primaryKey = 'id_template';
|
||||
protected $allowedFields = [
|
||||
'name',
|
||||
'subject',
|
||||
'body',
|
||||
'type'
|
||||
];
|
||||
protected $useTimestamps = true;
|
||||
protected $updatedField = 'updated_at';
|
||||
}
|
||||
@ -1,13 +0,0 @@
|
||||
<?php
|
||||
namespace App\Models;
|
||||
|
||||
class ThemeModel extends BaseModel
|
||||
{
|
||||
protected $table = 'auth_theme';
|
||||
protected $primaryKey = 'id_theme';
|
||||
protected $allowedFields = [
|
||||
'name',
|
||||
'type',
|
||||
'path'
|
||||
];
|
||||
}
|
||||
@ -1,12 +0,0 @@
|
||||
<?php
|
||||
namespace App\Models;
|
||||
|
||||
class TimezoneModel extends BaseModel
|
||||
{
|
||||
protected $table = 'auth_timezone';
|
||||
protected $primaryKey = 'id_timezone';
|
||||
protected $allowedFields = [
|
||||
'timezone',
|
||||
'description'
|
||||
];
|
||||
}
|
||||
Reference in New Issue
Block a user