random_string(); * ->random_number(); * ->get_visitor_ip(); * ->redirect('https://example.com'); * ->stringify(['key'=>'value']); * // various methods accepting objects in addition to array * ->array_merge($arg1, $arg2); * ->child_value($obj_or_array, $key, $default_value); * // various simplified file operations * ->file->read('/path/to/file.ext'); * ->file->write('/path/to/file.ext', 'content...'); * ->file->delete_directory('/path/to/dir'); * // caching (using simple local file caching) * ->cache->file->set('myKey', 'myValue'); * ->cache->file->get('myKey'); * // caching (using memcache) * ->cache->memcache->set('myKey', 'myValue'); * ->cache->memcache->get('myKey'); * ... * * // Note, if you use this library file in official plugins (hosted on services like wp.org or etc), remove all codes between regions titled "AUTOGENERATED_METHODS" in this file, because those codes is not accepted by revision system. */ namespace Puvox; if (!class_exists('\\Puvox\\library')) { #[\AllowDynamicProperties] class library { public function constant($name) { return defined($name) ? constant($name) : null; } public function property($propertyName) { return property_exists($this, $propertyName) ? $this->{$propertyName} : null; } #region debug public function dump($obj){ $content = $this->stringify($obj); //print_r($obj, true); $out = '
';
$out .= htmlentities( $this->br2nl( $content )) ;
try{
$trace = debug_backtrace();
if ( isset($trace[1]) )
$out .= ($this->is_cli() ? ' [' : '') .$this->array_value( $trace[1],'file','').':'.$this->array_value( $trace[1],'line',''). ($this->is_cli() ? '] ':'');
}
catch(\Exception $e){}
$out .= '';
exit ($out);
}
public function var_dump($obj){
ini_set("xdebug.var_display_max_children", '-1');
ini_set("xdebug.var_display_max_data", '10000');
ini_set("xdebug.var_display_max_depth", '-1');
echo ''; var_dump($obj); echo ''; } public function ExceptionMessage($ex, $extended=true){ return "Exception Message: {$ex->getMessage()} \r\n[{$ex->getTraceAsString()}] \r\n"; } //[{$ex->getFile()}::{$ex->getLine()}] public function stringify($data, $pretty=false) { if( $this->is_simple_type($data) ) { if ($pretty && $this->is_json($array_or_txt)) { return json_encode(json_decode($array_or_txt), JSON_PRETTY_PRINT); } return (!is_bool($data) ? $data : ($data? 'true':'false')); } else{ if (is_a($data, 'Exception')){ return print_r($data, true); //exception (https://pastebin_com/P73cgSkq) are only handled well by this } else{ return ( $pretty ? json_encode($data, JSON_PRETTY_PRINT) : json_encode($data)); } } } public static function uniqueId($args, $addition=''){ return md5(json_encode($args)."_$addition"); } #endregion public static function sleep($milliseconds){ if ( self::swoole_inside_coroutine() ) \Swoole\Coroutine\System::sleep($milliseconds / 1000); else { usleep($milliseconds*1000); } } public function force_redirect_to_https(){ if(!$this->is_https) { header("Location: https://" . $this->domainReal . $_SERVER["REQUEST_URI"], true, 301); exit; } } public static function current_url_contains($phrase, $case_sens=true){ return self::contains($_SERVER['REQUEST_URI'], $phrase, $case_sens); } public function get_visitor_ip() { $proxy_headers = array("CLIENT_IP", "FORWARDED", "FORWARDED_FOR", "FORWARDED_FOR_IP", "HTTP_CLIENT_IP", "HTTP_FORWARDED", "HTTP_FORWARDED_FOR", "HTTP_FORWARDED_FOR_IP", "HTTP_PC_REMOTE_ADDR", "HTTP_PROXY_CONNECTION", "HTTP_VIA", "HTTP_X_FORWARDED", "HTTP_X_FORWARDED_FOR", "HTTP_X_FORWARDED_FOR_IP", "HTTP_X_IMFORWARDS", "HTTP_XROXY_CONNECTION", "VIA", "X_FORWARDED", "X_FORWARDED_FOR"); foreach($proxy_headers as $proxy_header) { if (isset($_SERVER[$proxy_header])) { if(preg_match("/^([1-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])(\.([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])){3}$/", $_SERVER[$proxy_header])) { return $_SERVER[$proxy_header]; } else if (stristr(",", $_SERVER[$proxy_header]) !== FALSE) { $proxy_header_temp = trim(array_shift(explode(",", $_SERVER[$proxy_header]))); if (($pos_temp = stripos($proxy_header_temp, ":")) !== FALSE) {$proxy_header_temp = substr($proxy_header_temp, 0, $pos_temp); } if (preg_match("/^([1-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])(\.([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])){3}$/", $proxy_header_temp)) { return $proxy_header_temp; } } } } return ( !empty($_SERVER["REMOTE_ADDR"]) ? $_SERVER["REMOTE_ADDR"] : '__UNDEFINED_REMOTE_ADDR__'); } public function mail_scrambler($email) { return str_replace('@', '@', $email); } public function expire_headers() { ini_set('session.cookie_httponly', 1); //always display as new header("Cache-Control: no-cache, must-revalidate, max-age=0"); //expired in past header("Expires: ". date ('D, d M Y H:i:s', time() - 86400 *2) . " GMT"); header("Vary: Accept-Encoding"); header("Last-Modified: ". gmdate ("D, d M Y H:i:s", time() - 86400 *2) . " GMT"); } public function change_max_upload_post() { if (property_exists($this,'upload_max_limit')) { $this->upload_max_limit = max($this->upload_max_limit, ini_get('post_max_size')); ini_set('post_max_size', $this->upload_max_limit.'M'); ini_set('upload_max_filesize', upload_max_limit.'M'); ini_set('upload_max_size', upload_max_limit.'M'); } } #region url/path helpers public function br2nl($content) { return preg_replace('/\
'); // allowed: https://core.telegram.org/bots/api#html-style
$text = substr($text,0,4095); //max telegram message length 4096
$requestOpts = array_merge(['chat_id'=>$chat_id, 'text'=>$text], $extra_opts);
unset($requestOpts['is_repeated_call']);
$responseText = $this->get_remote_data( ['url'=>'https://api.telegram.org/bot'.$bot_key.'/sendMessage', 'post'=> $requestOpts]); // pastebin_com/u0J1Cph3 //'sendMessage?'.http_build_query($opts, '');
try {
$responseJson = json_decode($responseText);
// if it was successfull
if ($responseJson->ok)
{
return $responseJson;
}
// for some reason, if still unsupported format submitted, resubmit the plain format
//i.e. {"ok":false,"error_code":400,"description":"Bad Request: can't parse entities: Unsupported start tag \"br/\" at byte offset 43"}
else{
if (stripos($responseJson->description, 'Bad Request: can\'t parse entities') !==false){
if (! $is_repeated_call){
$text = "[SecondSend with stipped tags] \r\n". strip_tags($text) ;
$extra_opts['is_repeated_call'] = true;
return $this->telegram_message($text, $chat_id, $bot_key, $extra_opts);
}
}
return $responseJson;
}
} catch (Exception $ex) {
return ['ok'=>false, 'description'=> $ex->getMessage() . ':::' . $responseText];
}
}
public $telegram_interval_ms = 50; // telegram seems to accept around 30 times per second, so we'd better wait around that milliseconds
private $telegram_last_time=0;
public function telegram_message_cached($array, $botid){
$curMS = $this->timeMS();
$goneMS = $curMS - $this->telegram_last_time;
if ( $goneMS < $this->telegram_interval_ms ){
$this->sleep( $this->telegram_interval_ms - $goneMS);
}
$this->telegram_last_time = $curMS;
$key = $this->cache_key_create(array_merge($array, [$botid]));
if ( ! $this->is_cached_id('function__telegram_message_cached', $key) ){
$res= $this->telegram_message($array, $botid);
$ok='true';
}
else {
$res= (object)( ["ok"=>true, "success"=>false, 'reason'=>"$key was cached", 'content'=> json_encode($array) ] );
$ok='false';
}
if(is_callable([$this,'notifications_db_entry']))
$this->notifications_db_entry($key, $array['chat_id'], $this->stringify($res), time(), $ok );
return $res;
}
public function telegram_message_cached_with_channel($array, $botid){
$answer = $this->telegram_message_cached ( $array, $botid );
$this->telegram_channel_name_save($answer);
return $answer;
}
public function telegram_channel_name_save($response){
$existing = $this->telegram_channel_name_get();
$res = $response; //already decoded
if ( $this->array_value($res,'ok') )
{
// check to ensure (because cached ids dont have result)
if ( $this->array_value($res,'result') )
{
$id = $res->result->chat->id;
$title = $res->result->chat->title;
$type = $res->result->chat->type; //group or channel
$existing[$id] = (object)['title'=>$title, 'type'=>$type];
update_option('telegram_channel_names_temp', $existing);
}
}
}
public function telegram_channel_name_get($id=''){
$channelsArray = get_option('telegram_channel_names_temp',[]);
return !empty($id) ? $this->array_value($channelsArray, $id) : $channelsArray;
}
#endregion
// ################
// https://github.com/ttodua/useful-php-scripts/blob/master/get-remote-url-content-data.php
public static function get_remote_data($url, $post_params=null, $request_options=null)
{
return self::fetch($url, $post_params, $request_options);
}
public static function fetch($url, $post_params=null, $request_options=null)
{
$func = $post_params ? "wp_remote_post" : "wp_remote_get";
$is_wp = (function_exists($func));
$request_options = !empty($request_options)? $request_options : [];
if (!$is_wp)
{
return self::get_remote_data_callback($url, $post_params, $request_options);
}
else
{
if($func=="wp_remote_get") {
$out= wp_remote_get($url, $request_options );
}
if($func=="wp_remote_post") {
$post_array = (is_array($post_params)) ? $post_params : (parse_str($post_params , $new) ? $new : $new );
$args['body']=$post_array;
$args= array_merge($args, $request_options);
$out= wp_remote_post($url, $args );
//$out= call_user_func($func, $url, $args );
}
return wp_remote_retrieve_body($out); //same as $out['body']
}
return "empty_data. Create your own remote function";
}
public function get_remote_data_array($arr, $force_curl=false, $repeated_call=false)
{
if (is_array($arr))
{
$url = $arr['url'];
$post_params = $this->array_value($arr,'post', null);
$request_options= $this->array_value($arr,'options', []); if ($request_options==null) $request_options=[];
$should_be_json = $this->array_value($arr,'json', false);
$retry = $this->array_value($arr,'retry', true);
}
else{
$url = $arr;
$post_params = null;
$request_options=[];
$should_be_json = true;
$retry = true;
}
$request_options = array_merge_recursive($request_options, ['headers'=>['Cache-Control'=>'no-cache']] );
$data = $this->get_remote_data($url, $post_params, $request_options, $force_curl) ;
if (empty($data))
{
$res= (object)['error'=>'empty data', 'response'=>''];
}
else{
if ($should_be_json)
{
$dataTemp = $this->JsonData($data);
if (is_null($dataTemp))
$res= (object)['error'=>'not json', 'response'=>($data) ];
else
$res= (object)['error'=>false, 'response'=>json_decode($data) ];
/*
try {
$res= (object)['error'=>false, 'response'=>json_decode($data) ];
}
catch(\Exception $ex){
$res= (object)['error'=>'not json', 'response'=>($data) ];
}
*/
}
else{
$res= (object)['error'=>false, 'response'=>$data ];
}
}
// if still error, and retry allowed
if ($res->error && $retry && !$repeated_call)
{
$this->sleep(100);
$res = $this->get_remote_data_array($arr, $force_curl, $repeated_call=true);
}
return $res;
}
//i.e. set_cookies_from_url("http://example.com/?username=user&auth=key');
public function set_cookies_from_url($url)
{
$d=$this->get_remote_data($url, false, ["curl_opts"=>["CURLOPT_HEADERFUNCTION"=>
( function ($ch, $headerLine) {
if (preg_match('/^Set-Cookie:\s*([^;]*)/mi', $headerLine, $cookieArr) == 1)
{
$cookie = $cookieArr[1];
$cookie_vars = explode('=', $cookie, 2);
$this->example_cookies[$cookie_vars[0]] = $cookie_vars[1];
}
return strlen($headerLine); // Needed by curl
}
)
]]
);
foreach($this->example_cookies as $key=>$name)
{
$this->set_cookie($key,$name, 86000, '/target_dir/');
}
$this->set_cookie("sample_confirm","1");
}
// ----
public function get_client_ip() {
$proxy_headers = array("CLIENT_IP", "FORWARDED", "FORWARDED_FOR", "FORWARDED_FOR_IP", "HTTP_CLIENT_IP", "HTTP_FORWARDED", "HTTP_FORWARDED_FOR", "HTTP_FORWARDED_FOR_IP", "HTTP_PC_REMOTE_ADDR", "HTTP_PROXY_CONNECTION", "HTTP_VIA", "HTTP_X_FORWARDED", "HTTP_X_FORWARDED_FOR", "HTTP_X_FORWARDED_FOR_IP", "HTTP_X_IMFORWARDS", "HTTP_XROXY_CONNECTION", "VIA", "X_FORWARDED", "X_FORWARDED_FOR");
foreach($proxy_headers as $proxy_header) {
if (isset($_SERVER[$proxy_header])) {
if(preg_match("/^([1-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])(\.([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])){3}$/", $_SERVER[$proxy_header])) {
return $_SERVER[$proxy_header];
}
else if (stristr(",", $_SERVER[$proxy_header]) !== FALSE) {
$proxy_header_temp = trim(array_shift(explode(",", $_SERVER[$proxy_header])));
if (($pos_temp = stripos($proxy_header_temp, ":")) !== FALSE) {$proxy_header_temp = substr($proxy_header_temp, 0, $pos_temp); }
if (preg_match("/^([1-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])(\.([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])){3}$/", $proxy_header_temp)) { return $proxy_header_temp; }
}
}
}
return $_SERVER["REMOTE_ADDR"];
}
// $ipinfo = json_decode(get_ip_info($_SERVER['REMOTE_ADDR']), true);
// if($ipinfo['country_name'] != 'Georgia'){
public function get_ip_info($ip, $type=1, $api=""){
$info="";
if($type==1){
$info = $this->get_remote_data('https://geoip-db.com/json/'.$ip);
//"country_code":"GE", "country_name":"Georgia", "city":"null", "postal":null, "latitude":42, "longitude":43.5, "IPv4":"xxx.xxx.xxx.xxx", "state":"null"
}
elseif($type==2){
// PLEASE DONT USE THIS API
$info_initial = $this->get_remote_data('https://geoipify.whoisxmlapi.com/api/v1?apiKey='.$api.'&ipAddress='.$ip);
// {"ip":"xxx.xxx.xxx.xxx","location":{"country":"AU","region":"Victoria","city":"Research","lat":-37.7,"lng":145.1833,"postalCode":"3095","timezone":"Australia\/Melbourne"}}
$decoded = json_decode($info_initial, true);
$loc =$decoded['location'] ;
unset($decoded['location']) ;
$ipinfo_new = array_merge( $decoded,$loc );
return $ipinfo_new;
}
return $info;
}
public function output_js_headers()
{
session_cache_limiter('none');
// https://stackoverflow.com/a/1385982/2377343
$year=60*60*24*365;//year
//Caching with "CACHE CONTROL"
header('Cache-control: max-age='.$year .', public');
//Caching with "EXPIRES" (no need of EXPIRES when CACHE-CONTROL enabled)
//header('Expires: '.gmdate(DATE_RFC1123,time()+$year));
//To get best cacheability, send Last-Modified header and ...
header('Last-Modified: '.gmdate(DATE_RFC1123,filemtime(__file__))); //i.e. 1467220550 [it's 30 june,2016]
//reply using: status 304 (with empty body) if browser sends If-Modified-Since header.... This is cheating a bit (doesn't verify the date), but remove if you dont want to be cached forever:
// if (isset($_SERVER['HTTP_IF_MODIFIED_SINCE'])) { header('HTTP/1.1 304 Not Modified'); die(); }
header("Content-type: application/javascript; charset=utf-8");
}
public function input_fields_from_array($value, $keyname='', $replace_spaces=false){ //$keyname= (strpos($keyname,'[') === false) ? '['.$keyname.']' : $keyname;
echo '';
$this->input_fields_from_array_recursive($value, $keyname, $replace_spaces);
echo '';
}
public function input_fields_from_array_recursive($value, $keyname='', $replace_spaces=false){
if (!is_array($value)){
$height=30; $lines=explode("\r\n",$value);
foreach($lines as $eachLINE){
$height= $height+ceil(mb_strlen($eachLINE)/100) * 30;
}
// replace multiple whitespaces with single
$value = !$replace_spaces ? $value : preg_replace('!\s+!', ' ', str_replace("\t",' ', $value));
echo
'
'.$keyname.'
';
}
else{
echo ''.$keyname.'';
foreach ($value as $keyname1=>$value1){
echo '';
$this->input_fields_from_array_RECURSIVE($value1, $keyname.'['.$keyname1.']', $replace_spaces);
echo '';
}
}
}
public function random_color($alpha='FF') {
return '#' . str_pad(dechex(mt_rand(0, 0xFFFFFF)), 6, '0', STR_PAD_LEFT).$alpha;
}
public function content_height($content, $lineHeight=30){
$lines=explode("\n", $content);
$height = $lineHeight;
foreach($lines as $eachLINE){
$height = $height+ceil(mb_strlen($eachLINE)/100) * $lineHeight;
}
return $height;
}
public function js_autosize_textarea($classname=null)
{ ?> ';
foreach($array as $each) $out .=
'";
$out .= '';
return ''.$out.'';
}
public function loader($type="")
{
$circlecolor="#ffffff";
$head = '';
return $out;
}
public function get_user_browser(){
if (empty($_SERVER['HTTP_USER_AGENT'])) $_SERVER['HTTP_USER_AGENT']="unknown";
$b = $_SERVER['HTTP_USER_AGENT']; $final =array();
//(START FROM MOBILE check!!!!)
if(
preg_match('/android.+mobile|Windows Mobile|Nokia|avantgo|Mozilla(.*?)(Android|Mobile|Blackberry|Symbian)|OperaMini|Opera Mini|bada\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|ap|od)|iris|kindle|lge |maemo|meego.+mobile|midp|mmp|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\/|plucker|pocket|psp|series(4|6)0|symbian|treo|up\.(browser|link)|vodafone|wap|windows (ce|phone)|xda|xiino/i',$b)
||
preg_match('/1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\-(n|u)|c55\/|capi|ccwa|cdm\-|cell|chtm|cldc|cmd\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\-s|devi|dica|dmob|do(c|p)o|ds(12|\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\-|_)|g1 u|g560|gene|gf\-5|g\-mo|go(\.w|od)|gr(ad|un)|haie|hcit|hd\-(m|p|t)|hei\-|hi(pt|ta)|hp( i|ip)|hs\-c|ht(c(\-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\-(20|go|ma)|i230|iac( |\-|\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\/)|klon|kpt |kwc\-|kyo(c|k)|le(no|xi)|lg( g|\/(k|l|u)|50|54|\-[a-w])|libw|lynx|m1\-w|m3ga|m50\/|ma(te|ui|xo)|mc(01|21|ca)|m\-cr|me(di|rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\-2|po(ck|rt|se)|prox|psio|pt\-g|qa\-a|qc(07|12|21|32|60|\-[2-7]|i\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\-|oo|p\-)|sdk\/|se(c(\-|0|1)|47|mc|nd|ri)|sgh\-|shar|sie(\-|m)|sk\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\-|v\-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\-|tdg\-|tel(i|m)|tim\-|t\-mo|to(pl|sh)|ts(70|m\-|m3|m5)|tx\-9|up(\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas\-|your|zeto|zte\-/i',substr($b,0,4))
) { $final['brwsr'] = "Mobilee"; }
//if typical browsers
elseif(preg_match('/Firefox/i',$b)) { $final['brwsr'] = "Firefox"; }
elseif(preg_match('/Safari/i',$b)) { $final['brwsr'] = "Safari"; }
elseif(preg_match('/Chrome/i',$b)) { $final['brwsr'] = "Chrome"; }
elseif(preg_match('/Flock/i',$b)) { $final['brwsr'] = "Flock"; }
elseif(preg_match('/Opera/i',$b)) { $final['brwsr'] = "Opera"; }
elseif(preg_match('/MSIE 6/i',$b)) {$final['brwsr'] = "MSIE 6"; }
elseif(preg_match('/MSIE 7/i',$b)) {$final['brwsr'] = "MSIE 7"; }
elseif(preg_match('/MSIE 8/i',$b)) {$final['brwsr'] = "MSIE 8"; }
elseif(preg_match('/MSIE 9/i',$b)) {$final['brwsr'] = "MSIE 9"; }
elseif(preg_match('/MSIE 10/i',$b)) {$final['brwsr'] = "MSIE 10"; }
elseif(preg_match('/Trident\/7.0; rv:11.0/',$b)){$final['brwsr'] = "MSIE 11"; }
else {$final['brwsr'] = "UNKNOWNNN"; }
//===========================================================================================================
$final['full_brwsr_namee'] = $b;
//other parameters
return $final;
}
public function get_user_OS() {
if (empty($_SERVER['HTTP_USER_AGENT'])) $_SERVER['HTTP_USER_AGENT']="unknown";
$user_agent=$_SERVER['HTTP_USER_AGENT']; $final =array(); $final['os_namee']="_Unknown_OS_"; $final['os_typee']="_Unknown_OS_";
$os_array=array(
'MOUSED' => array(
'/windows nt 10.0/i'=>'Windows 10', '/windows nt 6.3/i'=>'Windows 8.1', '/windows nt 6.2/i'=>'Windows 8', '/windows nt 6.1/i'=>'Windows 7', '/windows nt 6.0/i'=>'Windows Vista','/windows nt 5.2/i'=>'Windows Server 2003/XP x64', '/windows nt 5.1/i'=>'Windows XP', '/windows xp/i'=>'Windows XP','/windows nt 5.0/i'=>'Windows 2000','/windows me/i'=>'Windows ME','/win98/i'=>'Windows 98','/win95/i'=>'Windows 95','/win16/i'=>'Windows 3.11',
'/macintosh|mac os x/i' =>'Mac OS X','/mac_powerpc/i'=>'Mac OS 9', '/linux/i'=>'Linux','/ubuntu/i'=>'Ubuntu',
),
'NOMOUSED' => array(
'/iphone/i'=>'iPhone','/ipod/i'=>'iPod','/ipad/i'=>'iPad','/android/i'=>'Android','/blackberry/i'=>'BlackBerry', '/webos/i'=>'Mobile'
)
);
foreach($os_array as $namee=>$valuee) { foreach ($valuee as $regex => $value1) { if(preg_match($regex, $user_agent)){$final['os_namee']=$value1; $final['os_typee'] = $namee;} } }
return $final;
}
// https://stackoverflow.com/a/31476046/2377343
public function get_url_parts($url,$part){ $x='';
$pURL = parse_url($url); $pthURL = pathinfo($url);
//for example: https://example.com/myfolder/sympony.mp3?aa=1&bb=2?cc=#gggg
if ($part=='scheme'){ $x = !empty($pURL['scheme']) ? $pURL['scheme'] :'';} // http
elseif ($part=='hostname'){ $x = !empty($pURL['host']) ? $pURL['host'] :'';} // example.com
elseif ($part=='query'){ $x = !empty($pURL['query']) ? $pURL['query'] :'';} // aa=1&bb=2?cc=
elseif ($part=='hash'){ $x = !empty($pURL['fragment']) ? $pURL['fragment'] :'';} // gggg
elseif ($part=='file'){ $x = !empty($pURL['path']) ? $pURL['path'] :'';} // /myfolder/sympony.mp3
elseif ($part=='filename'){ $x = !empty($pURL['path']) ? basename($pURL['path']) :'';} // sympony.mp3
elseif ($part=='extension'){ $x = !empty($pURL['path']) ? pathinfo($pURL['path'], PATHINFO_EXTENSION) :'';} // mp3
elseif ($part=='folder'){ $x = !empty($pURL['path']) ? dirname($pURL['path']) :'';} // /myfolder
elseif ($part=='dirname'){ $x = !empty($pthURL['dirname']) ? $pthURL['dirname'] :'';} // https://example.com/myfolder
elseif ($part=='afterfolder'){ $x = !empty($pthURL['basename'])? $pthURL['basename'] :'';} // sympony.mp3?aa=1&bb=2?cc=#ggg
return $x;
}
public function urlencodeall($x) {
$out = '';
for ($i = 0; isset($x[$i]); $i++) {
$c = $x[$i];
if (!ctype_alnum($c)) $c = '%' . sprintf('%02X', ord($c));
$out .= $c;
}
return $out;
}
// measure / timer for a function
public function function_benchmark($callback, $cycles_amount=1, $hint=''){
$before = microtime(true);
$val=[];
for ($i=0 ; $i<$cycles_amount; $i++) {
$val[]=call_user_func($callback);
}
$after = microtime(true);
echo "Time needed to execute $cycles_amount cycles:". self::number_format($after-$before, 5) . " sec\n
";
return $val;
}
public function json_encode_unicode($data){ return json_encode($data, JSON_UNESCAPED_UNICODE); }
public function utf8_declarationn() { return ''; }
public function utf8_declarationn_auto() { return ''; }
public function default_html_declaration($lng = 'en'){
return ' ';
}
public function default_rss_head_tags(){
?>
Enable Javascript in your Browser to avoid BROWSER problems!
';
return $out;
}
public function check_if_enabled_cookies(){ $out1 =
'';
return $out1;
}
public function old_browser_message($first=null, $incompatible_browsers=array('MSIE') ){
global $odd;
if (in_array($this->platforms()['brwsr'], $incompatible_browsers) ) { echo 'Your have an INCOMPATIBLE BROWSER! Please, use any modern browser (Firefox, Opera, Safari , Chrome..) to view site normally. '; }
}
public function facebook_rescarpe_url($url){ $x= $this->get_remote_data('https://graph.facebook.com/','id='.urlencode($url).'&scrape=true'); }
// ==================== text to image==============
// # Usage #
//text_to_image_my(
// $text='Helloooo World!' ,
// $separate_line_after_chars=40, $font='./Arial%20Unicode.ttf', $size=24, $rotate=0, $padding=0, $transparent=true, $color=['r'=>0,'g'=>0,'b'=>0], $bg_color=['r'=>255,'h'=>255,'b'=>255]
//);
public function text_to_image($text, $separate_line_after_chars=40, $font='./Arial%20Unicode.ttf',
$size=24,$rotate=0,$padding=2,$transparent=true, $color=array('r'=>0,'g'=>0,'b'=>0), $bg_color=array('r'=>255,'g'=>255,'b'=>255) ){
$amount_of_lines= ceil(strlen($text)/$separate_line_after_chars)+substr_count($text, '\n')+1;
$all_lines=explode("\n", $text); $amount_of_lines = count($all_lines); $text_final='';
foreach($all_lines as $key=>$value){
while( mb_strlen($value,'utf-8')>$separate_line_after_chars){
$text_final .= mb_substr($value, 0, $separate_line_after_chars, 'utf-8')."\n";
$value = mb_substr($value, $separate_line_after_chars, null, 'utf-8');
}
$text_final .= mb_substr($value, 0, $separate_line_after_chars, 'utf-8') . ( $amount_of_lines-1 == $key ? "" : "\n");
}
Header("Content-type: image/png");
$width=$height=$offset_x=$offset_y = 0;
// you can use: if (!file_exists($font)) filecreat('https://github.com/edx/edx-certificates/raw/master/template_data/fonts/Arial%20Unicode.ttf', $font);
// get the font height.
$bounds = ImageTTFBBox($size, $rotate, $font, "W");
if ($rotate < 0) {$font_height = abs($bounds[7]-$bounds[1]); }
elseif ($rotate > 0) {$font_height = abs($bounds[1]-$bounds[7]); }
else { $font_height = abs($bounds[7]-$bounds[1]);}
// determine bounding box.
$bounds = ImageTTFBBox($size, $rotate, $font, $text_final);
if ($rotate < 0){ $width = abs($bounds[4]-$bounds[0]); $height = abs($bounds[3]-$bounds[7]);
$offset_y = $font_height; $offset_x = 0;
}
elseif ($rotate > 0) { $width = abs($bounds[2]-$bounds[6]); $height = abs($bounds[1]-$bounds[5]);
$offset_y = abs($bounds[7]-$bounds[5])+$font_height; $offset_x = abs($bounds[0]-$bounds[6]);
}
else{ $width = abs($bounds[4]-$bounds[6]); $height = abs($bounds[7]-$bounds[1]);
$offset_y = $font_height; $offset_x = 0;
}
$height = $height + $font_height*($amount_of_lines+1);
$image = imagecreate($width+($padding*2)+1,$height+($padding*2)+1);
$background = ImageColorAllocate($image, $bg_color['r'], $bg_color['g'], $bg_color['b']);
$foreground = ImageColorAllocate($image, $color['r'], $color['g'], $color['b']);
if ($transparent) ImageColorTransparent($image, $background);
ImageInterlace($image, true);
// render the image
ImageTTFText($image, $size, $rotate, $offset_x+$padding, $offset_y+$padding, $foreground, $font, $text_final);
imagealphablending($image, true);
imagesavealpha($image, true);
// output PNG object.
imagePNG($image);
}
public function text_to_image2($your_text="heloooo", $width=250, $height=80)
{
$IMG = imagecreate( $width, $height );
$background = imagecolorallocate($IMG, 0,0,255);
$text_color = imagecolorallocate($IMG, 255,255,0);
$line_color = imagecolorallocate($IMG, 128,255,0);
imagestring( $IMG, 10, 1, 25, $your_text, $text_color );
imagesetthickness ( $IMG, 5 );
//imageline( $IMG, 30, 45, 165, 45, $line_color );
header( "Content-type: image/png" );
imagepng($IMG);
imagecolordeallocate($IMG, $line_color );
imagecolordeallocate($IMG, $text_color );
imagecolordeallocate($IMG, $background );
imagedestroy($IMG);
exit;
}
// https://mekshq.com/how-to-convert-hexadecimal-color-code-to-rgb-or-rgba-using-php/
public function hex2rgba($color, $opacity = false) {
$default = 'rgb(0,0,0)';
//Return default if no color provided
if(empty($color))
return $default;
//Sanitize $color if "#" is provided
if ($color[0] == '#' ) {
$color = substr( $color, 1 );
}
//Check if color has 6 or 3 characters and get values
if (strlen($color) == 6) {
$hex = array( $color[0] . $color[1], $color[2] . $color[3], $color[4] . $color[5] );
} elseif ( strlen( $color ) == 3 ) {
$hex = array( $color[0] . $color[0], $color[1] . $color[1], $color[2] . $color[2] );
} else {
return $default;
}
//Convert hexadec to rgb
$rgb = array_map('hexdec', $hex);
//Check if opacity is set(rgba or rgb)
if($opacity){
if(abs($opacity) > 1)
throw new \Exception("Opacity cant be more than 1");
$opacity = self::number_format((float)$opacity, 2);
$output = 'rgba('.implode(",",$rgb).','.$opacity.')';
} else {
$output = 'rgb('.implode(",",$rgb).')';
}
return $output;
}
// https://stackoverflow.com/a/5925612/2377343 | https://stackoverflow.com/questions/15852122/
public function hex_color($name){
$arr=['aliceblue'=>'F0F8FF', 'antiquewhite'=>'FAEBD7', 'aqua'=>'00FFFF', 'aquamarine'=>'7FFFD4', 'azure'=>'F0FFFF', 'beige'=>'F5F5DC', 'bisque'=>'FFE4C4', 'black'=>'000000', 'blanchedalmond '=>'FFEBCD', 'blue'=>'0000FF', 'blueviolet'=>'8A2BE2', 'brown'=>'A52A2A', 'burlywood'=>'DEB887', 'cadetblue'=>'5F9EA0', 'chartreuse'=>'7FFF00', 'chocolate'=>'D2691E', 'coral'=>'FF7F50', 'cornflowerblue'=>'6495ED', 'cornsilk'=>'FFF8DC', 'crimson'=>'DC143C', 'cyan'=>'00FFFF', 'darkblue'=>'00008B', 'darkcyan'=>'008B8B', 'darkgoldenrod'=>'B8860B', 'darkgray'=>'A9A9A9', 'darkgreen'=>'006400', 'darkgrey'=>'A9A9A9', 'darkkhaki'=>'BDB76B', 'darkmagenta'=>'8B008B', 'darkolivegreen'=>'556B2F', 'darkorange'=>'FF8C00', 'darkorchid'=>'9932CC', 'darkred'=>'8B0000', 'darksalmon'=>'E9967A', 'darkseagreen'=>'8FBC8F', 'darkslateblue'=>'483D8B', 'darkslategray'=>'2F4F4F', 'darkslategrey'=>'2F4F4F', 'darkturquoise'=>'00CED1', 'darkviolet'=>'9400D3', 'deeppink'=>'FF1493', 'deepskyblue'=>'00BFFF', 'dimgray'=>'696969', 'dimgrey'=>'696969', 'dodgerblue'=>'1E90FF', 'firebrick'=>'B22222', 'floralwhite'=>'FFFAF0', 'forestgreen'=>'228B22', 'fuchsia'=>'FF00FF', 'gainsboro'=>'DCDCDC', 'ghostwhite'=>'F8F8FF', 'gold'=>'FFD700', 'goldenrod'=>'DAA520', 'gray'=>'808080', 'green'=>'008000', 'greenyellow'=>'ADFF2F', 'grey'=>'808080', 'honeydew'=>'F0FFF0', 'hotpink'=>'FF69B4', 'indianred'=>'CD5C5C', 'indigo'=>'4B0082', 'ivory'=>'FFFFF0', 'khaki'=>'F0E68C', 'lavender'=>'E6E6FA', 'lavenderblush'=>'FFF0F5', 'lawngreen'=>'7CFC00', 'lemonchiffon'=>'FFFACD', 'lightblue'=>'ADD8E6', 'lightcoral'=>'F08080', 'lightcyan'=>'E0FFFF', 'lightgoldenrodyellow'=>'FAFAD2', 'lightgray'=>'D3D3D3', 'lightgreen'=>'90EE90', 'lightgrey'=>'D3D3D3', 'lightpink'=>'FFB6C1', 'lightsalmon'=>'FFA07A', 'lightseagreen'=>'20B2AA', 'lightskyblue'=>'87CEFA', 'lightslategray'=>'778899', 'lightslategrey'=>'778899', 'lightsteelblue'=>'B0C4DE', 'lightyellow'=>'FFFFE0', 'lime'=>'00FF00', 'limegreen'=>'32CD32', 'linen'=>'FAF0E6', 'magenta'=>'FF00FF', 'maroon'=>'800000', 'mediumaquamarine'=>'66CDAA', 'mediumblue'=>'0000CD', 'mediumorchid'=>'BA55D3', 'mediumpurple'=>'9370D0', 'mediumseagreen'=>'3CB371', 'mediumslateblue'=>'7B68EE', 'mediumspringgreen'=>'00FA9A', 'mediumturquoise'=>'48D1CC', 'mediumvioletred'=>'C71585', 'midnightblue'=>'191970', 'mintcream'=>'F5FFFA', 'mistyrose'=>'FFE4E1', 'moccasin'=>'FFE4B5', 'navajowhite'=>'FFDEAD', 'navy'=>'000080', 'oldlace'=>'FDF5E6', 'olive'=>'808000', 'olivedrab'=>'6B8E23', 'orange'=>'FFA500', 'orangered'=>'FF4500', 'orchid'=>'DA70D6', 'palegoldenrod'=>'EEE8AA', 'palegreen'=>'98FB98', 'paleturquoise'=>'AFEEEE', 'palevioletred'=>'DB7093', 'papayawhip'=>'FFEFD5', 'peachpuff'=>'FFDAB9', 'peru'=>'CD853F', 'pink'=>'FFC0CB', 'plum'=>'DDA0DD', 'powderblue'=>'B0E0E6', 'purple'=>'800080', 'red'=>'FF0000', 'rosybrown'=>'BC8F8F', 'royalblue'=>'4169E1', 'saddlebrown'=>'8B4513', 'salmon'=>'FA8072', 'sandybrown'=>'F4A460', 'seagreen'=>'2E8B57', 'seashell'=>'FFF5EE', 'sienna'=>'A0522D', 'silver'=>'C0C0C0', 'skyblue'=>'87CEEB', 'slateblue'=>'6A5ACD', 'slategray'=>'708090', 'slategrey'=>'708090', 'snow'=>'FFFAFA', 'springgreen'=>'00FF7F', 'steelblue'=>'4682B4', 'tan'=>'D2B48C', 'teal'=>'008080', 'thistle'=>'D8BFD8', 'tomato'=>'FF6347', 'turquoise'=>'40E0D0', 'violet'=>'EE82EE', 'wheat'=>'F5DEB3', 'white'=>'FFFFFF', 'whitesmoke'=>'F5F5F5', 'yellow'=>'FFFF00', 'yellowgreen'=>'9ACD32'];
return '#'.trim($this->array_value($arr, $name, 'FFFFFFFF'));
}
//addTextOnImage( ['text'=>'hello', 'input'=>'img.png', 'echo'=>false, 'method'=>'gd|imagick', 'fontsize'=>9, 'angle'=>-15, 'x'=>11, 'y'=>14, 'color'=>'#e7e7e7', 'opacity'=>0.5, 'stroke'=>['#e7e7e7',$width=4,$alpha=0.5], 'spaces'=>3]); //also, font
public function add_text_on_image($opts=[])
{
//v_dump(glob("C:\Windows\Fonts\*"));
//v_dump($Imagick->queryFonts("*"));
$text = $opts['text'];
$imagePath = $opts['input'];
$fontsize = $opts['fontsize'];
list($width, $height, $type, $attr) =getimagesize($imagePath);
$x_position = $this->array_value($opts,'x',0);
$y_position = $this->array_value($opts,'y',0);
if (strpos($x_position,'%')!==false) $x_position = $width * str_replace('%','',$x_position)/100;
if (strpos($y_position,'%')!==false) $y_position = $height * str_replace('%','',$y_position)/100;
if( $this->array_value($opts, 'text_repeat') === true)
{
$final_text="";
$multiplier=4; //lets say 3 for assurance
$spaces_between = $this->array_value($opts, 'spaces',5);
$repeated_per_width = ($width / (strlen($text) * $fontsize)) * $multiplier;
$repeated_per_height= ($height / ($fontsize)) * $multiplier;
for ($i=0; $i<$repeated_per_height; $i++)
{
$t= "";
for ($j=0; $j<$repeated_per_width; $j++)
{
$t .= $text . str_repeat(" ", $spaces_between );
}
$final_text .=$t. "\r\n";
}
$text = $final_text;
}
if ($this->array_value($opts, 'method') ==='gd')
{
// FETCH IMAGE & WRITE TEXT
$im = imagecreatefrompng($imagePath);
//imagecolorclosest imagecolorallocate
$red = imagecolorclosest($im, 0xFF, 0x00, 0x00);
$black = imagecolorclosest($im, 0x00, 0x00, 0x00);
$white = imagecolorclosest($im, 255, 255, 255);
// imagecolorallocate(imagecreatetruecolor(111, 111), 2, 2, 2)
//$color = $red;//$red;
imagefttext($im, $fontsize=$opts['fontsize'], $angle=$opts['angle'], $x_pos=$x_position, $y_pos=$y_position, $color=$opts['color'], $font=$opts['font'], $text);
imagealphablending($im, false);
imagesavealpha($im, true);
if ($resize=false)
{
$percent=0.5;
$new_width = $width * $percent;
$new_height = $height * $percent;
$image_p = imagecreatetruecolor($new_width, $new_height);
imagecopyresampled($im, $im, 0, 0, 0, 0, $new_width, $new_height, $width, $height);
}
// Output and free memory
header('Content-type: image/png');
imagepng($im);
imagedestroy($im);
}
else
{
// https://mlocati.github.io/articles/php-windows-imagick.html
// https://www.php.net/manual/en/book.imagick.php
$Imagick = new \Imagick();
$Imagick->readImage($imagePath);
$Imagick->setImageFormat( $format = $this->array_value($opts,'format','png') );
//$Imagick->setCompressionQuality ( 0 );
$ImagickDraw = new \ImagickDraw();
$ImagickDraw->setFontSize( $fontsize );
$ImagickDraw->setTextAntialias ( true );
if (array_key_exists('font',$opts) )
$ImagickDraw->setFont( $font=$opts['font'] );
if ( array_key_exists('stroke', $opts))
{
$ImagickDraw->setStrokeColor($opts['stroke'][0]);
$ImagickDraw->setStrokeWidth($opts['stroke'][1]);
$ImagickDraw->setStrokeOpacity($opts['stroke'][2]);
}
$ImagickDraw->setFillColor($color=$opts['color']);
$ImagickDraw->setFillOpacity($opacity=$opts['opacity']);
//$ImagickDraw->setGravity( Imagick::GRAVITY_CENTER );
$Imagick->annotateImage( $ImagickDraw, $x_pos=$x_position, $y_pos=$y_position, $angle=$opts['angle'], $text);
if ($opts['echo'])
{
header( "Content-Type: image/{$Imagick->getImageFormat()}" );
echo $Imagick->getImageBlob();
}
else{
$Imagick->writeImage($imagePath);
}
}
}
public function output_image($file=''){
if ( !in_array( $this->get_extension($file), ['jpg','jpeg','png','bmp','gif']) ) exit ('');
header("Content-type: image/png"); die( $this->file_get_contents($file) );
}
//not_founded_images_redirections (when on FTP, the file is not found, then automatically, the site is loaded.. so, in this case, use our function.
public function not_found_images_redirect() {
if (in_array( $this->get_url_parts($this->currentURL,'extension'), ['png','jpg','jpeg','gif','bmp','svg'])) {
echo 'Image error '; exit;
}
}
public function resize_image($imagePath, $width, $height=0, $auto_proportion=true, $filter=false, $blur=1)
{
$Imagick = new \Imagick();
$Imagick->readImage($imagePath);
//$Imagick->setImageFormat( $format = $this->array_value($opts,'format','png') );
$filter= !$filter ? \Imagick::FILTER_LANCZOS : $filter; //FILTER_LANCZOS
$Imagick->resizeImage($width, $height, $filter, $blur, $auto_proportion );
$Imagick->writeImage($imagePath);
}
//======helper function==========
//if(!function_exists('mb_substr_replace')){
function mb_substr_replace($string, $replacement, $start, $length = null, $encoding = "UTF-8") {
if (extension_loaded('mbstring') === true){
$string_length = (is_null($encoding) === true) ? mb_strlen($string) : mb_strlen($string, $encoding);
if ($start < 0) { $start = max(0, $string_length + $start); }
else if ($start > $string_length) {$start = $string_length; }
if ($length < 0){ $length = max(0, $string_length - $start + $length); }
else if ((is_null($length) === true) || ($length > $string_length)) { $length = $string_length; }
if (($start + $length) > $string_length){$length = $string_length - $start;}
if (is_null($encoding) === true) { return mb_substr($string, 0, $start) . $replacement . mb_substr($string, $start + $length, $string_length - $start - $length); }
return mb_substr($string, 0, $start, $encoding) . $replacement . mb_substr($string, $start + $length, $string_length - $start - $length, $encoding);
}
return (is_null($length) === true) ? substr_replace($string, $replacement, $start) : substr_replace($string, $replacement, $start, $length);
}
//}
//if(!function_exists('mb_str_word_count')){
function mb_str_word_count($string, $format = 0, $charlist = '[]') {
$string=trim($string);
if(empty($string)){$words = array();} else {$words = preg_split('~[^\p{L}\p{N}\']+~u',$string);}
switch ($format) { case 0: return count($words); break; case 1: case 2: return $words; break; default: return $words; break; }
}
//}
public function header_mail($from=false, $host= false){
$from = $from ? $from : "contact";
$host = $host ? $host : $_SERVER['HTTP_HOST'];//$_SERVER['SERVER_ADDR'];
return array('From: '.$from.'@'.$host . "\r\n" . 'Reply-To: '.$from.'@'.$host . "\r\n" . 'X-Mailer: PHP/' . phpversion());
}
public function value_or_input_field($namee){
if (!empty($GLOBALS['editing_inputs'])){
}
else{
}
}
public function ksort_recursive(&$array) {
foreach ($array as &$value) {
if (is_array($value)) $this->ksort_recursive($value);
}
return ksort($array);
}
public function die_if_array_key($array, $key){ if (array_key_exists($key, $array)) exit($array[$key]); }
public function chars_array_($alhpanumeric=true){ return ( $alhpanumeric ?
array('0','1','2','3','4','5','6','7','8','9','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z')
:
array('!','$','+','<','[',']','%',',','.','=','&','-','<','>','|', '"', '\'', '\\', '~','(','/',')','!',' ',"\r","\n", '*', '{','}','?','`','@',':',';','^')
);
}
public function preg_quote_fast($text){
$specs =array('/', '.','\\','+','*','?','[','^',']','$','(',')','{','}','=','!','<','>','|',':','-');
$new_array_for_strtr = array();
foreach($specs as $each){
$new_array_for_strtr[$each] = '\\'.$each;
}
$text = strtr( $text, $new_array_for_strtr);
return $text;
}
public function checkboxes($checkbox_name,$current_value, $unchecked_value,$checked_value){
$out = ''; return $out;
}
public function js_library($url_or_Tag=true, $defaultPath=""){
if( empty($defaultPath) && function_exists('home_url') )
$defaultPath = plugin_dir_url($this->plugin_entryfile);
$url = $defaultPath . '/libray_standard.js';
return $url_or_Tag ? $url : '';
}
public function my_translate_month_inside($string = '27/January/2015'){
foreach($GLOBALS['odd']['months_arr'] as $each){
if(strpos($string,$each)!==false) {
$string = str_replace($each,translate__MONTH($each), $string);
}
}
return $string;
}
public function my_utf8_decode($textt){
$var = $textt; $var = iconv("UTF-8","ISO-8859-1//IGNORE",$var); $var = iconv("ISO-8859-1","UTF-8",$var); $var = str_replace(' ','',$var);
return $var;
}
// ============================================= YOUTUBE DOWNLOAD FUNCTIONS ====================================================
// https://pastebin_com/bFePMkfy
// https://img.youtube.com/vi/XXXXXXXXX/0.jpg (a bit larger) // 1,2,3
// https://img.youtube.com/vi/xxxxxxxxx/mqdefault.jpg
// https://img.youtube.com/vi/xxxxxxxxx/hqdefault.jpg
// https://img.youtube.com/vi/xxxxxxxxx/maxresdefault.jpg
public function get_youtube_thumbnail($id,$quality='maxres'){return 'https://i.ytimg.com/vi/'.$id.'/'.$quality.'.jpg';}
//to check if variable are normal
public function get_youtube_id_from_url($url) {
preg_match('/(http(s|):|)\/\/(www\.|)youtu(be\.com|\.be)\/(embed\/|watch.*?v=|)([a-z_A-Z0-9\-]{11})/i', $url, $results);
return (isset($results[6]) ? $results[6] : false);
}
public function get_youtube_id_from_contents($url){
if (stripos($url,'youtu.be/')!==false) {preg_match('/(https:|http:|)(\/\/www\.|\/\/|)(.*?)\/(.{11})/si', $url, $final_ID); $x= !empty($final_ID[4]) ? $final_ID[4] : '';}
elseif (stripos($url,'youtube.com/')!==false) {preg_match('/(https:|http:|)(\/\/www\.|\/\/|)(.*?)\/(embed\/|watch.*?v=|)([a-z_A-Z0-9\-]{11})/si', $url, $IDD);$x= !empty($IDD[5]) ? $IDD[5] : ''; }
return (!empty($x) ? $x : '');
}
public function validate_youtube_id($id){ if (strlen($id)!=11 || preg_match('/[\<\>\'\=\$\"\?\(\{]/si',$text)) {die("incorrrrrect_ID_ error79"); }}
//#################################
// force ssl
public function redirect_to_https(){
if(empty($_SERVER['HTTPS']) || $_SERVER['HTTPS'] === "off")
{
$redirect = $this::sanitize_url('https://' . $_SERVER['HTTP_HOST'] . $_SERVER['REQUEST_URI']);
header('HTTP/1.1 301 Moved Permanently');
header('Location: ' . $redirect);
exit();
}
}
public function redirect_to_nonwww($https=true){
if( stripos($_SERVER['HTTP_HOST'],'www.') !== false ) {
$redirect = ($https ? 'https' : 'http') . '://' . str_replace('www.','', $_SERVER['HTTP_HOST']) . $_SERVER['REQUEST_URI'];
header('HTTP/1.1 301 Moved Permanently');
header('Location: ' . $redirect);
exit();
}
}
public function serialized_fixer($serialized_string){
// securities
if (empty($serialized_string)) return '';
if ( !preg_match('/^[aOs]:/', $serialized_string) ) return $serialized_string;
if ( @unserialize($serialized_string) !== false ) return $serialized_string;
return
preg_replace_callback(
'/s\:(\d+)\:\"(.*?)\";/s',
function ($matches){ return 's:'.strlen($matches[2]).':"'.$matches[2].'";'; },
$serialized_string )
;
}
public function img_urlencode($imgUrl){
return str_replace('/'.basename($imgUrl) , '/'.str_replace('+','%20',basename($imgUrl)), $imgUrl);
}
public function img_urlencode2($imgUrl){
preg_match('/(.*)\/(.*)/si',$imgUrl, $n); $x = (!empty($n[1]) && !empty($n[2])) ? $n[1].'/'.str_replace('+','%20',urlencode($n[2])) : "error_29858"; return $x;
}
// i.e. get_remote_data(' tinyurl.com/api-create.php?url='.$url);
public function get_short_link($url) { return $url; }
public function allowed_extensions_of_url( $url ) {
$ext = array( 'jpeg', 'jpg', 'gif', 'png' );
$info = (array) pathinfo( parse_url( $url, PHP_URL_PATH ) );
return isset( $info['extension'] ) && in_array( strtolower( $info['extension'] ), $ext, TRUE );
}
public function m1($tag=""){ $this->var_dump("\r\n
* [MemoryUsage]A$tag :". $this->memory_usage()); }
public function memory_usage(){ return memory_get_usage()/pow(1024,2); }
public function gc_enable(){ return gc_enable(); }
public function gc_clean() { return gc_collect_cycles(); }
// create: https://vectr.com/new https://vectorpaint.yaks.co.nz/
// convert : https://hnet.com/png-to-svg/ ( https://image.online-convert.com/convert-to-svg | https://convertio.co/ )
// view: https://www.rapidtables.com/web/tools/svg-viewer-editor.html
public function images($which, $type="png", $url_or_tag=true)
{
$url=[];
switch ($which)
{
//see visually: https://i.imgur.com/MNxlU7s.png
case "overlay-pro" : $url['svg'] = ' '; break;
//see visually: https://i.imgur.com/6oHljXM.png
case "questionMark-1" : $url['svg'] = ' '; break;
//see visually: https://i.imgur.com/73R7eLv.png
case "questionMark-2" : $url['svg'] = ' Layer 1 Â ?
'; break;
//see visually: https://i.imgur.com/mx70WNM.png
case "rating-transparent" : $url['svg'] = ' '; break;
//see visually: https://upload.wikimedia.org/wikipedia/commons/b/b5/PayPal.svg
case "paypal" : $url['svg'] = ' '; break;
}
return $url[$type];
}
public function encode_svg($content){ return str_replace(['<','>', '#', '"'], ['%3C','%3E', '%23', '\''], $content); }
public function image_svg($which){ return 'data:image/svg+xml;charset=UTF-8,'. $this->encode_svg( $this->images($which, 'svg') ); }
public function question_mark($text, $dialog=0, $question_mark="") {
$mouseover='';
$content = '';
if($dialog==0){
$content = $text;
}
else if($dialog==1){
$content = '';
$mouseover = ' onmouseover="jQuery(\'#\'+this.parentNode.id).tooltip({ items:this, content:\''.$text.'\', show: { effect: \'blind\', duration: 800 } }).tooltip(\'open\');"';
}
else if($dialog==2){
$content = '';
$mouseover = ' onmouseover="jQuery(\''.$text.'\').dialog({ modal:true, width:600 });"';
}
if (empty($question_mark)) $question_mark=$this->image_svg('questionMark-1');
return '
';
}
public function between($a,$b,$c){
return ($a<$b && $b<$c);
}
public function inside($a,$b,$c){
return ($this->between($a,$b,$c) || $this->between($c,$b,$a) );
}
public static $nodepath='';
public static function node_exec($filepath){
//process.stdout.write("hii");
return empty(self::$nodepath) ? 'Node path not set' : self::cmd(self::$nodepath .' '.$filepath);
}
#region ############### ASYNC FUNCTIONS ############### //
// https://www.reddit.com/r/PHP/comments/no7abs/
public $async_methods_available = ['reactphp', 'amphp', 'amphp_parallel', 'spatie','parallel','fibers', 'swoole', 'exec', 'proc-open', 'popen', 'pcntl_fork', '_no_async_' ];
// to execute non-blocking async callback-function | args: [$func,$args] where $args is array
public function async_function($callback, $which_method='spatie'){
$method = strtolower($which_method);
if ( !in_array( $method, $this->async_methods_available) )
throw new \Exception( "$method not supported, use from: ". implode(' | ',$this->async_methods_available) );
$func_name = 'async_functions_helper_'.$method;
call_user_func([$this,$func_name], [ [$callback, $arg1=[]] ] );
}
// to execute blocking/non-blocking call of multiple gourp for async callback-functions
// ####### EXAMPLE #######
//
// $func = function($param1=null, $param2=null, ... ){
// echo "\nParams are : ". print_r(func_get_args(),true);
// };
//
// $arr = [ [$func], [$func, "hi"], [$func, "good", "bye"] ] ;
// $helpers->async_functions($arr,'parallel');
public function async_functions($callbacksArray, $which_method='spatie', $blocking=true, $exception_handler=null){
$method = strtolower($which_method);
if ( !in_array( $method, $this->async_methods_available) )
throw new \Exception( "$method not supported, use from: ". implode(' | ',$this->async_methods_available) );
$example = ': CALLBACK & ARGUMENT pair, like [$callback,$arg1,...] or [$callback], where $args behaves like as in call_user_func_array';
if ( !is_array($callbacksArray) )
throw new \Exception("async_functions was passed incorrect argument. Should be array of $example");
$callbacksArray_NEW =[]; // just add arguments
foreach($callbacksArray as $eachPair){
if (is_callable($eachPair))
{
$callbacksArray_NEW[] = [$eachPair, []];
}
elseif (is_array($eachPair))
{
$callback = $eachPair[0];
array_shift($eachPair); //unset first one, as all other ones are arguments passed to call_user_func
$args = empty($eachPair)? [] : $eachPair;
$callbacksArray_NEW[] = [$callback, $args];
}
else{
throw new \Exception("async_functions was passed incorrect array of callback. Each array child should be $example");
}
}
//re-sort
$func_name = 'async_functions_helper_'.$method;
call_user_func([$this, $func_name], $callbacksArray_NEW, $exception_handler);
return;
if ($blocking)
{
}
else{
//foreach($callbacksArray_NEW as $callbackAndArgPair){
// $this->async_function($callbackAndArgPair, $which_method);
//}
}
}
// ##### PARALLEL (requires extension) #####
public static function async_functions_helper_parallel($callbacksArray, $exception_handler=null)
{
foreach( $callbacksArray as $callback_arg_pair){
//\parallel\run($callback = $callback_arg_pair[0], $args = $callback_arg_pair[1] );
//$r1 = new \parallel\Runtime();$r1->run
self::async_function_parallel($callback = $callback_arg_pair[0], $args = $callback_arg_pair[1]);
}
}
public static function async_function_parallel($callback, $args=[])
{
\parallel\run($callback, $args);
}
// ##### SPATIE ##### [ https://github.com/spatie/async/issues/120 ]
public static function async_functions_helper_spatie($callbacksArray, $exception_handler=null)
{
if ( ! self::spatieSupported() ){
$msg = "Spaties needed extensions are not enabled: pcntl & posix";
//if ( !$this->is_localhost()) throw new \Exception($msg); else
self::var_dump($msg . " ; However, continuing execution in synchronous mode");
}
$pool = \Spatie\Async\Pool::create();
foreach( $callbacksArray as $callback_arg_pair){
$pool->add( function() use($callback_arg_pair){
call_user_func_array($callback = $callback_arg_pair[0], $args = $callback_arg_pair[1]);
} )->then(function ($output) {
// Handle success
})->catch(function (\Spatie\Async\Pool\Throwable $exception) {
var_dump($exception);
});
}
$pool->wait();
} public static function spatieSupported(){ return \Spatie\Async\Pool::isSupported(); }
// ##### SWOOLE (requires extension) #####
// use advanced usage: https://www.swoole.co.uk/docs/modules/swoole-coroutine-run
public static function async_functions_helper_swoole($callbacksArray, $exception_handler=null)
{
// needs to be checked ( as: https://www.swoole.co.uk/docs/modules/swoole-coroutine-run )
if (self::swoole_installed() && function_exists('\\Swoole\\Coroutine\\run') )
{
if ( !self::swoole_inside_coroutine() )
{
\Swoole\Coroutine\run(function() use ($callbacksArray,$exception_handler) {
self::async_functions_helper_swooleGoTrigger($callbacksArray,$exception_handler);
});
}
else{
self::async_functions_helper_swooleGoTrigger($callbacksArray,$exception_handler);
}
}
else{
var_dump("Swoole not installed, running plain function");
self::async_functions_helper__no_async_($callbacksArray);
}
}
private static function async_functions_helper_swooleGoTrigger($callbacksArray, $exception_handler=null)
{
//$wg = new \Swoole\Coroutine\WaitGroup();
foreach( $callbacksArray as $callback_arg_pair){
\go(function() use ($callback_arg_pair, $exception_handler) {
try{
//$wg->add(1);
call_user_func_array($callback = $callback_arg_pair[0], $args = $callback_arg_pair[1]);
//$wg->done();
}
catch(\Exception $ex){
if (is_callable($exception_handler))
call_user_func($exception_handler, new \Exception($ex->getMessage()) );
else
trigger_error($ex->getMessage());
}
});
}
//$wg->wait();
}
public static function swoole_inside_coroutine(){ return (self::swoole_installed() && \Swoole\Coroutine::getCid()!=-1 && \Swoole\Coroutine::getPcid()!==false ); } // https://cloud.tencent.com/developer/article/1771756
public static function swoole_inside_coroutine_run(){ return (self::swoole_installed() && \Swoole\Coroutine::getPcid()==-1); }
public static function swoole_inside_coroutine_go(){ return (self::swoole_installed() && is_numeric(\Swoole\Coroutine::getPcid()) && \Swoole\Coroutine::getPcid()>0); }
public static function swoole_installed(){ return class_exists('\\Swoole\\Coroutine'); }
public static function helper_SwooleToggle($enable_or_disable ){
// SWOOLE_HOOK_ALL; // https://www.geeksforgeeks.org/php-bitwise-operators/ ::: swoole_hook_all is: 2147479551 | SWOOLE_HOOK_CURL : 2048 | SWOOLE_HOOK_NATIVE_CURL : 4096 \Swoole\Runtime::getHookFlags(); // $currentHooks ^ SWOOLE_HOOK_CURL ^ SWOOLE_HOOK_NATIVE_CURL; <-- cannot enable both | \Swoole\Runtime::setHookFlags($final); // https://github.com/swoole/swoole-src/issues/4280
if (!self::swoole_inside_coroutine())
return;
if($enable_or_disable)
\Swoole\Runtime::setHookFlags(SWOOLE_HOOK_ALL);
else
\Swoole\Runtime::setHookFlags(0);
}
// ##### AMPHP #####
public static function async_functions_helper_reactphp($callbacksArray, $exception_handler=null){
$loop = \React\EventLoop\Factory::create();
$promise = new \React\Promise\Promise(function($resolve){
});
foreach($callbacksArray as $callback_arg_pair) {
$promise->then(function($v) use ($loop, $callback_arg_pair, $exception_handler) {
$loop->run( function() use($callback_arg_pair, $exception_handler){
try{
call_user_func_array($callback = $callback_arg_pair[0], $args = $callback_arg_pair[1]);
}
catch(\Exception $ex){
if (is_callable($exception_handler))
call_user_func($exception_handler,$ex);
else
trigger_error($ex->getMessage());
}
} );
});
}
$loop->run();
}
// ##### AMPHP #####
public static function async_functions_helper_amphp($callbacksArray, $exception_handler=null){
$promises = [];
\Amp\Loop::run(function () use($callbacksArray) {
foreach($callbacksArray as $eachCallbackAndArg) {
\Amp\Loop::defer($eachCallbackAndArg[0]);
}
});
return;
//...
$promises[] = \Amp\call( function() use ($eachCallbackAndArg) {
return call_user_func($eachCallbackAndArg[0],$eachCallbackAndArg[1]);
} );
//\Amp\Loop::run(); \Amp\asyncCall
\Amp\Promise\wait(\Amp\Promise\all($promises));
return;
// ..
\Amp\asyncCall( function() use ($eachCallbackAndArg) {
return call_user_func($eachCallbackAndArg[0],$eachCallbackAndArg[1]);
} );
\Amp\Loop::run();
}
// https://github.com/amphp/parallel-functions && https://github.com/amphp/parallel-functions/issues/28
public static function async_functions_helper_amphp_parallel($callbacksArray, $exception_handler=null){
foreach($callbacksArray as $callback_arg_pair) {
//$pool = new \Amp\Parallel\Worker\DefaultPool();
$callbacks[] = call_user_func_array(\Amp\ParallelFunctions\parallel($callback_arg_pair[0]), $callback_arg_pair[1]); //, $pool
}
$result = \Amp\Promise\wait(\Amp\Promise\all($callbacks));
}
// ##### EXEC #####
// https://stackoverflow.com/questions/49592786/asynchronous-call-to-shell-exec-php
// https://stackoverflow.com/questions/222414/asynchronous-shell-exec-in-php
// https://stackoverflow.com/questions/45953/php-execute-a-background-process#45966
// https://stackoverflow.com/questions/2212635/best-way-to-manage-long-running-php-script !!
public static function async_functions_helper_exec($command = null, $with_php=false){
// moved to separate file, due to WP restrictions
return self::async_functions_helper_exec2($command, $with_php);
}
// no async, just default fallback
public static function async_functions_helper__no_async_($callbacksArray, $exception_handler=null)
{
self::call_user_funcs($callbacksArray);
}
public static function call_user_funcs($callbacksArray)
{
foreach($callbacksArray as $callbackAndArgsPair){
call_user_func_array($callbackAndArgsPair[0], $callbackAndArgsPair[1]);
}
}
#endregion
// get-timezones : pastebin_com/4tXjgY7B
public function add_prefix_to_object_keys($object, $prefix){
$new_object = new stdClass();
foreach ($object as $k => $v) {
$new_object->{$prefix . $k} = $v;
}
return $new_object;
}
public function convert_timeframe_into_seconds($input="4h", $minute_symbol="m", $month_symbol="M")
{
$array=['s'=>1,'S'=>1, 'm'=>60, 'h'=>3600,'H'=>3600, 'd'=>86400,'D'=>86400, 'w'=>604800,'W'=>604800, 'M'=>2678400];//31days
foreach($array as $key=>$value)
{
if ( strpos($input,$key)!==false ) { $input=str_replace($key,'', $input); $input=$input*$value; }
}
return $input;
}
public function die_pretty($html){
$html =
''.
''.$html.'
'.
'';
exit ($html);
}
// custom always-loaded scripts
// my_script_url("css|js", "public|admin")
public function my_script_url($type="js|css", $kind="public|admin", $with_tag=false)
{
if ($type=='js'){
return ($with_tag? '':'');
}
elseif ($type=='css'){
return ($with_tag? '':'');
}
}
public function my_loader_css_js($css=true, $js=true)
{
$admin = function_exists('is_admin') ? is_admin() : false;
if ($css) echo $this->my_script_url('css', ( $admin ? 'admin':'public'), true);
if ($js) echo $this->my_script_url('js', '', true);
}
public function my_loader_css_js_trigger()
{
$screen= is_admin()? 'admin' : 'public';
$this->my_loader_css_js($css=$this->load_styles['css'][$screen], $js=$css=$this->load_styles['js'][$screen]);
}
// ================================== STYLES ================================== //
private $all_enqueue_scripts=[];
public function init_loadscripts($override_array)
{
$initial_scripts=
[
//
'my_javascript' => ['screen'=>['admin'=>0, 'public'=>0], 'urls'=>[
'js' => $this->my_script_url('js','')
]],
'my_style_public'=> ['screen'=>['admin'=>0, 'public'=>0], 'urls'=>[
'css' => $this->my_script_url('css','public')
]],
'my_style_admin'=> ['screen'=>['admin'=>0, 'public'=>0], 'urls'=>[
'css' => $this->my_script_url('css','admin')
]]
];
$this->load_scripts_override = [];
if ( method_exists($this, 'define_load_links') ) $this->define_load_links();
$initial_scripts = array_merge($initial_scripts, $this->load_scripts_override);
$this->all_enqueue_scripts = array_replace_recursive($initial_scripts, $override_array);
}
public function my_styles_hook($pure_php=false) {
$front_or_back = function_exists('is_admin') && is_admin() ? 'admin' : 'public';
$current_screen = $front_or_back=='public' ? 'wp' : 'admin'; // gets: admin or public
foreach ($this->all_enqueue_scripts as $name=>$block)
{
if($block['screen'][$front_or_back])
{
if (!empty($block['urls']))
foreach ($block['urls'] as $JS_or_CSS=>$url)
{
$type_ = ($JS_or_CSS=="js") ? 'script' : ($JS_or_CSS=="css" ? 'style' : $JS_or_CSS);
if ($pure_php===true)
{
if ($type_=='style')
echo '';
else {
echo '';
}
}
else
{
$this->register_stylescript($current_screen, $type_, $name, $url);
}
}
}
}
}
//example testmode : pastebin_com/bUncPcFD
public function filedate($file){
return date("Y-M-D--H-i-s", filemtime($file) );
}
//if ( !$this->above_version('5.4') ) { echo("php_version is ". PHP_VERSION ." (quite old). HIGHLY recomended to update to higher version, or this program might not funciton normally ". __FILE__ ); }
public function above_version($version= "5.4"){
return version_compare(phpversion(), $version, '>=');
}
public function noindex_meta_tag() { return ''; }
public function randomId($divider="_"){ return "K".time() . $divider . rand(1,9).rand(0,9999999999999); }
// #####################################
//check either GET or argv (note, in argv, the parameters should be quoted, like:
// * * * * * /usr/bin/php -q /var/www/example/wp-cron.php "cron_cycle=3¶m=1"
public static function argvs($key='', $default='')
{
global $argv;
$array = [];
if (!empty($argv[1])) {
parse_str($argv[1], $array);
}
return $array;
}
public static function argv($key='', $default='')
{
global $argv;
$array = [];
if (!empty($argv[1])) {
parse_str($argv[1], $array);
}
return empty($key) ? $array : ( array_key_exists($key, $array) ? $array[$key] : $default);
}
public function get($key='', $default='')
{
return empty($key) ? $_GET : ( array_key_exists($key, $_GET) ? $_GET[$key] : $default);
}
// THIS IS ALWAYS SANITIZED IN IMPLEMENTATIONS
public function post($key='', $parsePhpInput=true){
if (!empty($_POST)) {
$array = $_POST;
} else {
$input = file_get_contents('php://input');
if (!empty($input)) {
if (!$parsePhpInput) return $input;
$array= json_decode($input, true);
if (is_null($array))
{
return $input;
}
} else{
$array = [];
}
}
return (!empty($key) ? $this->array_value($array,$key) : $array);
}
public function inputData(){
return $this->POST();
}
public function argv_or_get($key='', $default=null)
{
global $argv;
$array = [];
if (!empty($argv[1])) {
parse_str($argv[1], $array);
}
else {
$array=$this->Get();
}
return !empty($key) ? $this->array_value($array,$key,$default) : $array;
}
public function argv_is_set($key)
{
global $argv;
$array = [];
if (!empty($argv[1])) {
parse_str($argv[1], $array);
}
return array_key_exists($key,$array);
}
public function argv_or_get_is_set($key)
{
global $argv;
$array = [];
if (!empty($argv[1])) {
parse_str($argv[1], $array);
}
else {
$array=$this->Get();
}
return array_key_exists($key,$array);
}
public static function argv_called_file()
{
global $argv;
return !empty($argv[0]) ? $argv[0] : '';
}
public static function is_cron(){ return self::is_cli(); }
public static function is_cli(){
try{
if( defined('STDIN') ) return true;
if( empty($_SERVER['REMOTE_ADDR']) && !isset($_SERVER['HTTP_USER_AGENT']) && count($_SERVER['argv']) > 0) return true;
$sapi_type = php_sapi_name();
return (substr($sapi_type, 0, 3) == 'cli' || empty($_SERVER['REMOTE_ADDR']));
}
catch(\Exception $ex){
}
return false;
}
public static function array_to_argv($array=null)
{
$str = http_build_query($array);
return $str;
}
//convert command line to array like _GET
public function argv_to_array($argv_=null,$index=1)
{
$array=[];
if (!empty($argv_[$index])) parse_str($argv_[$index], $array);
return $array;
}
public static function php_path_current(){ return PHP_BINARY; }
public static function command_current($addToParams=''){
return self::php_path_current().' "'.self::ArgvFile().'" "'.self::array_to_argv(self::Argv()) .$addToParams.'"';
}
public static function is_simple_type($var){
return ( is_string($var) || is_numeric($var) || is_bool($var) );
}
public function argvs_get_post($argv_,$index=1)
{
//$array=[];
//if (!empty($argv_[$index])) parse_str($argv_[$index], $array);
return $array;
}
public function serialize_argv($argvs)
{
if(empty($argvs) || !is_array($argvs)) return $argvs;
$new_ar=[];
foreach($argvs as $key=>$value)
{
if(stripos($value,'=')===false)
{
$new_ar[$key] = $value;
}
else{
parse_str($argvs[$key], $params);
$key1=array_keys($params)[0];
if(!empty($argvs) && is_array($params))
$new_ar[$key1] = $params[$key1];
}
}
return $new_ar;
}
// #####################################
public function array_fields($array, $parent="plugin_slug[sample][sub]", $pairs=false)
{
echo '';
echo '';
if (is_array($array) && !empty($array))
{
foreach ($array as $optName=>$value)
{
echo $this->field_out_helper1($parent, $optName, $value, $pairs) ;
}
}
$sample_field = $this->field_out_helper1($parent, "", "", $pairs);
//echo $sample_field;
echo '';
?>
sanitize_nonoword($parent); ?>
';
}
public function field_out_helper1($parent, $optName, $value, $pairs)
{
$output='';
$rand= "inputKey_".rand(1,999999)."_".rand(1,999999)."_".rand(1,999999);
if (!$pairs) {
$key = (!empty($optName) ? $optName : $rand);
$output .= '';
} else {
$output .= '';
$output .= '';
}
$output .='';
return $output;
}
public function array_sanitize_text_field($ar)
{
$new=[];
foreach($ar as $key=>$val)
{
$new[ $this->sanitize_text_field($val["name"]) ] = $this->sanitize_text_field($val["value"]);
}
return $new;
}
public function get_fb_name_regex($fb_url){
preg_match('/'.preg_quote('^(?:https?://)?(?:www.|m.|touch.)?(?:facebook.com|fb(?:.me|.com))/(?!$)(?:(?:\w)#!/)?(?:pages/)?(?:[\w-]/)?(?:/)?(?:profile.php?id=)?([^/?\s])(?:/|&|?)?.*$/'), $fb_url, $n);
return $n[1];
}
// shapeSpace
public function allowed_html_tags() {
$allowed_tags = [
'a' => [
'class'=>[], 'href'=>[], 'rel'=>[], 'title'=>[],
],
'abbr' => [
'title' => [],
],
'b' => [],
'blockquote' => [
'cite' => [],
],
'cite' => [
'title' => [],
],
'code' => [],
'del' => [
'datetime'=>[], 'title'=>[],
],
'dd' => [],
'div' => [
'class'=>[], 'title'=>[], 'style'=>[],
],
'dl' => [],
'dt' => [],
'em' => [],
'h1' => [],
'h2' => [],
'h3' => [],
'h4' => [],
'h5' => [],
'h6' => [],
'i' => [],
'img' => [
'alt'=>[], 'class'=>[], 'height'=>[], 'src'=>[], 'width'=>[],
],
'li' => [
'class'=>[],
],
'ol' => [
'class'=>[],
],
'p' => [
'class'=>[],
],
'q' => [
'cite'=>[],'title'=>[],
],
'span' => [
'class'=>[], 'title'=>[], 'style'=>[],
],
'strike' => [],
'strong' => [],
'ul' => [
'class' => [],
]
];
return $allowed_tags;
}
public function display_errors()
{
ini_set('display_errors', 1);
ini_set('display_startup_errors', 1);
error_reporting( E_ALL );
}
public function log_errors($path=false, $callback=null)
{
//htaccess:
// php_flag log_errors on
// php_value error_log /home/FTP_username/public_html/error_log.txt
ini_set("log_errors", 1);
ini_set("error_log", $path ? $path : $_SERVER['DOCUMENT_ROOT']."/zzz___php-my-errors_".$this->my_site_variables__secret('rand_name', random_string(11)).".log");
//error_log( "Hello, errors!" );
if (!is_null($callback)) set_error_handler($callback);
}
public function javascript_headers()
{
session_cache_limiter('none');
// http://stackoverflow.com/a/1385982/2377343
//Caching with "CACHE CONTROL"
header('Cache-control: max-age='.($year=60*60*24*365) .', public');
//Caching with "EXPIRES" (no need of EXPIRES when CACHE-CONTROL enabled)
//header('Expires: '.gmdate(DATE_RFC1123,time()+$year));
//To get best cacheability, send Last-Modified header and ...
header('Last-Modified: '.gmdate(DATE_RFC1123,filemtime(__file__))); //i.e. 1467220550 [it's 30 june,2016]
//reply using: status 304 (with empty body) if browser sends If-Modified-Since header.... This is cheating a bit (doesn't verify the date), but remove if you dont want to be cached forever:
// if (isset($_SERVER['HTTP_IF_MODIFIED_SINCE'])) { header('HTTP/1.1 304 Not Modified'); die(); }
header("Content-type: application/javascript; charset=utf-8");
}
public function set_log_dir($dir)
{
$this->logDir = $dir;
$this->mkdir($this->logDir);
}
public function form_from_array($value, $fullKeyName='', $replace_spaces=false, $url='')
{
?>
arFieldAutoresize)
$this->js_autosize_textarea('.valueTxtArea');
?>
';
}
$keyName_BOLDED = preg_replace('/(.*)\[(.*?)\]/','$1[$2]', $fullKeyName);
$is_parent_array = !is_array($value) || !array_key_exists('languages', $value) ;
echo '';
$style = ' style=""';
if ( !is_array($value) ){
echo '
'. $keyName_BOLDED .'
';
}
else{
echo '
'. $keyName_BOLDED .'
';
$addButtonOnKey=false;
foreach ($value as $keyname1=>$value1){
if ($keyname1==$addButtonKeyName) {
continue;
}
$keyname1 = $this::sanitize_text($keyname1);
$newKeyNm = $fullKeyName.'['.$keyname1.']';
echo '';
// if array contains empty_placeholder, then it was meant for Adding/Removing for keys
if (array_key_exists($addButtonKeyName, $value))
{
$addButtonOnKey=true;
echo '-delete';
}
$this->arFieldRecRastKey=$keyname1;
$this->input_fields_from_array_recursive2($value1, $newKeyNm, $replace_spaces, $cycle+1);
echo '';
}
echo '';
if ($addButtonOnKey)
{
echo '+ADD';
}
echo '
';
}
echo '';
if ($cycle==0)
{
echo '';
}
}
public function move_folder_contents($from, $to)
{
foreach( glob($from ."/*") as $each)
{
$target=$to."/".basename($each);
if(is_dir($target)) {
//$this->rmdir_recursive($target);
}
elseif(is_file($target))
{
@unlink($target);
//rename($each, $target);
}
}
}
public function js_debugmode($name='debugmode')
{
if ( ! defined('PUVOX_js_debugmode') )
{
define('PUVOX_js_debugmode', true);
$this->debugmode_script = '';
add_action('wp_head', function(){ echo $this->debugmode_script; }, 1);
add_action('admin_head',function(){ echo $this->debugmode_script; }, 1);
}
}
// REGEXES
public function preg_replace_if_inside($str, $phrase, $start, $end)
{
return preg_replace("/(?<=". preg_quote($start).")(.*?|)". $phrase ."(.*?|)(?=".preg_quote($end).")/si", '', $str);
}
public function split_by_X_not_inside_YZ($str, $by, $y, $z) //y&z: not inside
{
return preg_split( '/'.$by.'+(?=(?:(?:[^'.$y.']*"){2})*[^'.$z.']*$)/si', $str );
}
public function get_from_X_till_Y_not_inside($content, $from, $till, $array, $regex_index=0, $remove_outside=true)
{
$from_ = $from; //this.escapeRegExp(from);
preg_match( '/'. $from_ ."(.*)/si", $content, $matches );
$result = "";
if ($matches != null )
{
$regex_index_final = $regex_index+1;
$foundPart= $matches[$regex_index_final];
$splits = $this->split_by_X_not_inside($foundPart, $till, $array);
$result = trim($splits[0]);
}
return $result;
}
// ############### REGEXES ###############
public function get_current_buffer_clean($func_name=false){ ob_start(); if ($func_name) {$args=func_get_args(); call_user_func_array($func_name, $args);} $cont= ob_get_clean(); ob_flush(); return $cont; }
// youtube old funcs - get_video_info: pastebin_com/HWeaHFVJ
// php memory ram shared caching: pastebin_com/CpkkA43x
// ### ERRORS TABLE ### //
public function sqlite_error_db_init($db_dir=false, $db_name=false, $PLA=[], $TELEGRAM=[])
{
$sqlite_db_path= $db_dir . $db_name;
$db = $this->sqlite_db_init( $sqlite_db_path );
$this->SQLITE_ERRORS_DB_INSTANCE = $db;
}
public function sqlite_error_table_create($db, $tablename)
{
$db->exec( "CREATE TABLE IF NOT EXISTS {$tablename} (
id INTEGER PRIMARY KEY,
title TEXT,
text TEXT,
status TEXT,
url TEXT,
time INTEGER)"
);
}
public function sqlite_error_log($db, $tablename, $title, $text, $status=null)
{
$db = $db ?: $this->SQLITE_ERRORS_DB_INSTANCE;
$this->sqlite_error_table_create($db, $tablename);
$sql = 'INSERT INTO '.$tablename.'(title,text,status,url,time) VALUES( "'.($title ?: '').'", "'.($text ?: '').'", "'.($status ?: '').'", "'.$this->requestURL.'" , "'. time().'")';
//if ( ! $this->helpers->is_localhost ) $this->helpers->telegramMsg( $this->tg_errorbot['key'], $this->tg_errorbot['chat'], $title .'::::'. $text);
return $db->exec($sql);
}
public function slog($title, $text, $db=null, $tablename='all_errors')
{
return $this->sqlite_error_log($db, $tablename, $title, $text);
}
// ##################### //
#region PHP to PHP/C# encryption/description :
// https://puvox.software/blog/two-way-encryption-decryption-between-php-and-c-sharp/
//public static class EncryptDecrypt {
public static function encrypt($plaintext, $password, $method= 'aes-256-cbc'){
self::helper__encrypt_decrypt_stream($password);
return base64_encode(openssl_encrypt($plaintext, $method, self::password_shuffled, OPENSSL_RAW_DATA, self::iv));
}
public static function decrypt($encrypted, $password, $method= 'aes-256-cbc'){
self::helper__encrypt_decrypt_stream($password);
return openssl_decrypt(base64_decode($encrypted), $method, self::password_shuffled, OPENSSL_RAW_DATA, self::iv);
}
public static function helper__encrypt_decrypt_stream($password, $method= 'aes-256-cbc'){
// Must be exact 32 chars (256 bit)
self::$password_shuffled = substr(hash('sha256', $password, true), 0, 32);
// IV must be exact 16 chars (128 bit)
self::$iv = chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0) . chr(0x0);
}
//}
#endregion
// --- LOCAL OPTIONS APPROACH ---
public function site_options_path(){
return $this->baseDIR.'/_site_options.json';
}
public function get_site_options_all(){
if (property_exists($this,'JSON_CACHED_ALL_OPTIONS'))
{
return $this->JSON_CACHED_ALL_OPTIONS;
}
$path = $this->site_options_path();
if (!file_exists($path)){
$this->localdata_set($path,'{"all_options":{}}');
}
$this->JSON_CACHED_ALL_OPTIONS = json_decode( $this->file_get_contents($path), []);
return $this->JSON_CACHED_ALL_OPTIONS;
}
public function save_site_options_all($opts){
$path = $this->site_options_path();
$this->localdata_set($path, $opts);
}
public function update_option_json($option_name, $value){
$path = $this->site_options_path();
$opts= $this->get_site_options_all();
if (!is_array($option_name)){
$opts['all_options'][$option_name] = $value;
}
else{
$c = count($option_name);
$o = $option_name;
if ($c==2) $opts[ $o[0] ][ $o[1] ] = $value;
if ($c==3) $opts[ $o[0] ][ $o[1] ][ $o[2] ] = $value;
if ($c==4) $opts[ $o[0] ][ $o[1] ][ $o[2] ][ $o[3] ] = $value;
if ($c==5) $opts[ $o[0] ][ $o[1] ][ $o[2] ][ $o[3] ][ $o[4] ] = $value;
if ($c==6) $opts[ $o[0] ][ $o[1] ][ $o[2] ][ $o[3] ][ $o[4] ][ $o[5] ] = $value;
if ($c==7) $opts[ $o[0] ][ $o[1] ][ $o[2] ][ $o[3] ][ $o[4] ][ $o[5] ][ $o[6] ] = $value;
if ($c==8) $opts[ $o[0] ][ $o[1] ][ $o[2] ][ $o[3] ][ $o[4] ][ $o[5] ][ $o[6] ][ $o[7] ] = $value;
}
$this->JSON_CACHED_ALL_OPTIONS = $opts;
try { $this->localdata_set($path, json_encode($opts)); } catch (\Exception $e){ die($e->getMessage()); }
return true;
}
public function get_option_json($option_name, $default_value=''){
$opts = $this->get_site_options_all() ;
if (!is_array($option_name)){
return ( array_key_exists($option_name, $opts['all_options']) ? $opts['all_options'][$option_name] : $default_value );
}
else{
$new_val = $opts;
foreach($option_name as $val)
{
$new_val = $new_val[$val];
}
return $new_val;
}
}
public function set_default_options( $array, $key_name ){
$opts = $this->get_site_options_all();
if (!array_key_exists($key_name, $opts)){
$opts[$key_name]=[];
}
foreach($array as $key=>$value){
if ( !array_key_exists($key, $opts[$key_name]) ){
$opts[$key_name][$key] = $value;
$this->update_option_json([$key_name, $key], $value);
}
}
return $opts[$key_name];
}
public function get_child($array, $name)
{
if (!is_array($name))
return $array[$name];
else{
$new_val = $array;
foreach($name as $val)
{
$new_val = $new_val[$val];
}
return $new_val;
}
}
//
// algo-related functions
public function highest($values, $length)
{
$amount= count($values);
$last= max(array_keys($values));//might be empty initial X keys, so dont use "count"
$index = $last;
$highest= $values[$last];
if ($length >= 1){
for ($i=0; $i $highest){
$highest = $values[$idx];
$index=$idx;
}
}
}
}
return ["value"=>$highest, "index"=>$index];
}
public function lowest($values, $length)
{
$amount= count($values);
$last= max(array_keys($values));//might be empty initial X keys, so dont use "count"
$index = $last;
$lowest= $values[$last];
if ($length >= 1){
for ($i=0; $i$lowest, "index"=>$index];
}
public function zip_folder ($input_folder, $output_zip_file) {
$zipClass = new ZipArchive();
if($input_folder !== false && $output_zip_file !== false)
{
$res = $zipClass->open($output_zip_file, \ZipArchive::CREATE);
if($res === TRUE) {
// Add a Dir with Files and Subdirs to the archive
$foldername = basename($input_folder);
$zipClass->addEmptyDir($foldername);
$foldername .= '/'; $input_folder .= '/';
// Read all Files in Dir
$dir = opendir ($input_folder);
while ($file = readdir($dir)) {
if ($file == '.' || $file == '..') continue;
// Rekursiv, If dir: GoodZipArchive::addDir(), else ::File();
$do = (filetype( $input_folder . $file) == 'dir') ? 'addDir' : 'addFile';
$zipClass->$do($input_folder . $file, $foldername . $file);
}
$zipClass->close();
}
else { exit ('Could not create a zip archive, migth be write permissions or other reason. Contact admin.'); }
}
}
#region ================ INIT ================
public function init_defaults()
{
try{
//some of this can be overwriten by init_module
$this->ip = $this->get_visitor_ip();
$this->isMobile = false;
$this->isWP = defined("ABSPATH");
$this->is_cli = $this->is_cli();
$this->is_development = defined("_puvox_machine_") ; // set only in devmachine (in "my_superglobals.php" and in "EnvVariables")
//only web parts
$this->is_https = $this->is_cli ? false : ((!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS']!=='off') || (!empty($_SERVER['SERVER_PORT']) && $_SERVER['SERVER_PORT']==443) );
$this->https = $this->is_cli ? 'https://': ( $this->is_https ? 'https://' : 'http://');
$this->domainCurrent = $this->is_cli ? '' : (!empty($_SERVER['HTTP_HOST']) ? $_SERVER['HTTP_HOST'] : '');
$this->domain = $this->is_cli ? '' : $this->https . $this->domainCurrent;
$this->requestURL = $this->is_cli ? '' : $this->array_value($_SERVER,'REQUEST_URI'); $this->requestURI=$this->requestURL;
$this->currentURL = $this->is_cli ? '' : $this->domain.$this->requestURL;
$this->domainCurrentWithoutPort=$this->is_cli ? '' : $this->array_value( parse_url($this->currentURL),'host');
$this->is_localhost = $this->is_cli ? false : $this->is_localhost();
// others
$this->empty_image = "data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 1 1'></svg>";
$this->extra_options_enabled=false;
}
catch(\Exception $ex){
$this->var_dump($ex);
}
}
// only when called explicitly, i.e. from plugin or module
public function init_module($args=[])
{
// Because this is a class, we don't use "__FILE__" & "__DIR__" here, but "Reflection" to refer to caller file ####
$isClass=(array_key_exists('class',$args) && !empty($args['class']));
$reflection = $isClass ? (new \ReflectionClass( $args['class'] )) : null;
$this->module_NAMESPACE = $isClass ? $reflection->getNamespaceName() : (array_key_exists('NAMESPACE',$args) ? $args['NAMESPACE'] : "EXAMPLE"); // get parent's namespace name
$this->moduleFILE = $isClass ? $reflection->getFileName() : (array_key_exists('FILE',$args) ? $args['FILE'] : __FILE__); // set plugin's main file path
$this->moduleDIR = (array_key_exists('DIR',$args) ? $args['DIR'] : dirname($this->moduleFILE) ).DIRECTORY_SEPARATOR ; // set plugin's dir path
$this->prefix = strtolower( preg_replace('![^A-Z]+!', '', $this->module_NAMESPACE) );// get prefix from current namespace initials of UpperCase characters (i.e. MyPluginNamespace-->MPN)
$this->prefix_ = $this->prefix .'_';
//$backtrace = debug_backtrace(); $this->_index_file_ = $backtrace[0]['file']; $this->_index_dir_ = dirname($this->_index_file_);
// if this class is used just as a helper php library
if (!$this->isWP || array_key_exists('homeFOLDER', $args))
{
$this->homeFOLDER = $args['homeFOLDER'];
$this->homeURL = $this->domain.$this->homeFOLDER;
$this->doc_root_real = $this->slash_replace_direction(str_replace( $this->homeFOLDER,'', $this->slash_replace_direction($this->moduleDIR, 'forward') ), 'forward'); // even for symlinked;
$this->moduleURL = str_replace($this->doc_root_real,'', $this->slash_replace_direction($this->moduleDIR, 'forward')) ;
}
// else, if this class is used as plugin class (used mostly by Puvox.Software)
else
{
$this->wpURL = network_home_url('/'); // WP installation home
$this->wpFOLDER = network_home_url('/', 'relative'); // WP folder
$this->homeURL = home_url('/'); // current sub/site home url
$this->homeFOLDER = home_url('/', 'relative'); // current sub/site home folder
$this->moduleURL = plugin_dir_url($this->moduleFILE); //
$this->plugin_entryfile = defined( $this->module_NAMESPACE.'\\PLUGIN_ENTRY_FILE') ? constant($this->module_NAMESPACE.'\\PLUGIN_ENTRY_FILE') : $this->moduleFILE;
}
$this->httpsReal = preg_replace('/(http(s|):\/\/)(.*)/i', '$1', $this->homeURL);
$this->domainReal = $this->get_domain_from_url($this->homeURL); $this->domainNaked=$this->domainReal;
$this->domain = $this->httpsReal.$this->domainReal;
$this->domain_schemeless= '//'.$this->domainReal;
$this->site_slug = str_ireplace('.','_', $this->domainReal);
$this->urlAfterHome = substr($this->requestURL, strlen($this->homeFOLDER) );
$this->pathAfterHome = parse_url($this->urlAfterHome, PHP_URL_PATH);
$this->homeUrlStripped = $this->remove_http_www($this->homeURL);
$this->baseFILE = $this->moduleFILE; //
$this->baseDIR = $this->moduleDIR.'/'; //
$this->baseURL = property_exists($this, 'baseURL') ? $this->baseURL : $this->moduleURL; //( stripos(__FILE__, 'wp-content'.DIRECTORY_SEPARATOR.'themes') !== false ? themeURL ...
$this->baseScriptsFolder= property_exists($this, 'baseScriptsFolder') ? $this->baseScriptsFolder : '';
$this->baseScriptsDir = $this->baseDIR . $this->baseScriptsFolder;
$this->baseScriptsUrl = $this->baseURL . $this->baseScriptsFolder;
$this->changeable_JS_CSS_version = ( file_exists($file = $this->baseScriptsDir.'/style-public.css') ? 'date_'.filemtime($file) : $this->sanitize_key($this->domainReal).date('m') );
// others
$this->is_development = defined("_puvox_machine_") ; // set only in devmachine (in "my_superglobals.php" and in "EnvVariables")
if ($this->is_development)
{
$this->display_errors();
if (!property_exists($this,'triggered_dev_shutdown_hook'))
{
$this->triggered_dev_shutdown_hook=true;
register_shutdown_function( function(){ if (substr(ob_get_contents(), -7)=='') echo('');} );
$this->START_TIME1 = microtime(true);
register_shutdown_function( function(){ if (substr(ob_get_contents(), -7)=='') echo('');} );
}
}
}
private $privateAppName__ = null;
public function set_app_name ($name){ $this->privateAppName__ = $name; }
public function get_app_name() {
if (!$this->privateAppName__){
throw new \Exception ('Before you start using caching functions, please at first define your appplication\'s name(identifier) at first with .->set_app_name ("whatever_my_app_name"), so it will get its own cache-storage identifier');
}
return $this->privateAppName__;
}
public function __construct()
{
$this->file = new \Puvox\tempclass_file($this);
$this->cache = new \Puvox\tempclass_cache($this);
$this->init_defaults();
}
#endregion
// ##############################################################
// ##################### CUSTOM FUNCTIONS #######################
// ##############################################################
// DO_NOT_OT_REMOVE_THIS_LINE___
// ##############################################################
// ################# END - CUSTOM FUNCTIONS #####################
// ##############################################################
} // class
#[\AllowDynamicProperties]
class tempclass_file {
public function __construct($parent){
$this->parent = $parent;
}
public function temp_dir() {
return $this->parent::slash_trailing (sys_get_temp_dir());
}
/*
static function _getTempDir()
{
$tmp_locations = array('/tmp', '/var/tmp', 'c:\WUTemp', 'c:\temp', 'c:\windows\temp', 'c:\winnt\temp');
$tmp = ini_get('upload_tmp_dir');
if (!strlen($tmp)) {
$tmp = getenv('TMPDIR');
}
while (!strlen($tmp) && count($tmp_locations)) {
$tmp_check = array_shift($tmp_locations);
if (@is_dir($tmp_check)) {
$tmp = $tmp_check;
}
}
return strlen($tmp) ? $tmp : false;
}
*/
public function exists ($filePath) {
return file_exists($filePath) || is_dir($filePath);
}
public function mtime ($filePath) {
if ($this->exists($filePath)) {
return filemtime ($filePath)*1000;
} else {
return null;
}
}
public function unlink ($filePath) {
return unlink($filePath);
}
//public function mkdir($dest, $permissions=0755, $create=true){ return $this->mkdir_recursive($dest, $permissions, $create); }
//public function mkdir_recursive(
public function create_directory($dirPath, $permissions=0755, $create=true) {
if(!is_dir($dirPath)){
//at first, recursively create parent directory if doesn't exist
$parent = dirname($dirPath);
if( $parent && !is_dir($parent) ){ $this->create_directory($parent, $permissions, $create); }
else {
if ( is_writable( $parent ) ){
return mkdir($dirPath, $permissions, $create);
}
else{
var_dump("No permission to create directory: $parent");
return false;
}
}
}
return true;
}
//rmdir rmdir_recursive
public function delete_directory($dirPath) {
if(!empty($dirPath) && is_dir($dirPath) ){
$dir = new \RecursiveDirectoryIterator($dirPath, \RecursiveDirectoryIterator::SKIP_DOTS); //upper dirs not included,otherwise DISASTER HAPPENS :)
$files = new \RecursiveIteratorIterator($dir, \RecursiveIteratorIterator::CHILD_FIRST);
foreach ($files as $path) $path->isDir() && !$path->isLink() ? $this->delete_directory($path->getPathname()) : unlink($path->getPathname()); //{if (is_file($path)) {unlink($path);} else {$empty_dirs[] = $path;} } if (!empty($empty_dirs)) {foreach ($empty_dirs as $eachDir) {rmdir($eachDir);}}
rmdir($dirPath);
return true;
}
return true;
//include_once(ABSPATH.'/wp-admin/includes/class-wp-filesystem-base.php');
//\WP_Filesystem_Base::rmdir($fullPath, true);
}
public function read($filePath, $defaultContent = ''){
if (!$this->exists($filePath)){
return $defaultContent;
}
return $this->parent->file_get_contents($filePath);
}
public function write($filePath, $content){
$dir = dirname($filePath);
$this->create_directory($dir);
return $this->parent->file_put_contents($filePath, $content);
}
public function get_files_list_from_dir ($dir) {
$filesList = [];
// todo
return $filesList;
}
/*
public function emptyDir($dirPath){
return array_map( 'unlink', array_filter((array) glob("$dirPath/*") ) );
}
public function copy_recursive($source, $dest, $permissions = 0755){
if (is_link($source)) { return symlink(readlink($source), $dest); }
elseif (is_file($source)) {
if(!file_exists(dirname($dest))){$this->create_directory(dirname($dest), $permissions, true); }
if(!copy($source, $dest)) {echo "not copied ($source ---> $dest )";} return true;
}
elseif (is_dir($source)) {
$this->create_directory($dest, $permissions, true);
foreach (glob($source.'/*') as $each){ $basen= basename($each);
if ($basen != '.' && $basen != '..') { $this->copy_recursive("$each", "$dest/$basen", $permissions); }
}
}
}
*/
} // templcass_file
#[\AllowDynamicProperties]
class tempclass_cache {
public function __construct($parent){
$this->parent = $parent;
$this->file = new \Puvox\tempclass_cache_file($this->parent);
}
} // templcass_cache
#[\AllowDynamicProperties]
class tempclass_cache_file {
public function __construct($parent){
$this->parent = $parent;
}
public $customCacheDir = null;
public function get_dir() {
if (!$this->customCacheDir) {
$this->customCacheDir = $this->parent->file->tempDir();
}
$finaldir = $this->parent::slash_trailing ($this->customCacheDir . '_cache_' . $this->parent->get_app_name());
return $finaldir;
}
public function set_dir($dir, $auto_clear_seconds=null){
if($dir) $this->customCacheDir = $dir;
$res = $this->parent->file->create_directory($this->customCacheDir);
if( !is_null($auto_clear_seconds))
{
throw new \Exception("Not implemented yet! 345346");
//$this->clearCacheDir($auto_clear_seconds);
}
return $res;
}
public function file_path($uniqFileName){
$uniqFileName = is_string($uniqFileName) || is_numeric($uniqFileName) ? $uniqFileName : json_encode($uniqFileName);
$uniqFileName = $this->parent::sanitize_key_dashed($this->parent::chars_from_start($uniqFileName, 15)) . "_" . md5($uniqFileName);
$filePath= $this->get_dir() . $uniqFileName . "_tmp";
return $filePath;
}
//
public function get($uniqFileName, $defaultContent='', $expire_seconds=8640000, $decode = true)
{
$filePath = $this->file_path($uniqFileName);
if ( $this->parent->file->exists($filePath) ){
if ($this->parent->file->mtime($filePath) + $expire_seconds*1000 < time()*1000){
$this->parent->file->unlink($filePath);
return $defaultContent;
}
else{
$cont = $this->parent->file->read($filePath, null);
// if specifically array, then on empty, reckon as array
if ($cont===null)
{
return $defaultContent;
}
if ($decode){
try{
return json_decode($cont, true);
}
catch(\Exception $e){
return $cont;
}
}
else{
return $cont;
}
}
}
else {
return $defaultContent;
}
}
public function set($uniqFileName, $content)
{
$filePath= $this->file_path($uniqFileName);
$contentFinal = is_string($content) ? $content : ((is_array($content) || parent.isObject($content)) ? json_encode($content) : $content);
return $this->parent->file->write($filePath, $contentFinal);
}
//
// public function writeFileAppendJson(filePath, jsonContent, callback){
// try{
// var callback = callback || function(){};
// var self = this;
// puvox_library.modules('fs').readFile(filePath, 'utf8', function(err,data) {
// let json = {};
// if (typeof data !="undefined" && data!=''){
// json=JSON.parse(data);
// }
// let jsonNew = self.jsonConcat(json, jsonContent);
// let content = JSON.stringify(jsonNew);
// puvox_library.modules('fs').writeFile(filePath, content, 'utf8', function(callback_) {
// });
// });
// }
// catch(e){
// console.log("writeFileAppendJson", e);
// }
// },
public $containerDefaultPrefix= "_cached_ids_";
public $tempIds =[];
public function id_for_content($slugOrContent){
return md5($this->parent->is_simple_type($slugOrContent) ? $slugOrContent : json_encode($slugOrContent));
}
public function exists_id($containerSlug, $id){
return array_key_exists($id, $this->get_ids($containerSlug));
}
public function get_ids($containerSlug) {
if (! array_key_exists($containerSlug, $this->tempIds)) {
$content = $this->parent->file->read($this->get_dir() . $this->containerDefaultPrefix . $containerSlug, '{}');
$this->tempIds[$containerSlug] = json_decode($content, true);
}
return $this->tempIds[$containerSlug];
}
public function set_ids($containerSlug, $idsDict) {
$this->tempIds[$containerSlug] = $idsDict;
return $this->parent->file->write($this->get_dir() . $this->containerDefaultPrefix . $containerSlug, json_encode($this->tempIds[$containerSlug]));
}
public function add_id($containerSlug, $id){
$ids = $this->get_ids($containerSlug);
$ids[$id] = 1;
$this->set_ids($containerSlug, $ids);
}
public function add_id_if_not_exists($containerSlug, $id){
if (! $this->exists_id($containerSlug, $id)){
$this->add_id($containerSlug, $id);
return true;
}
return false;
}
/*
#region ################ CACHE ###############
public function cache_get($key, $default=null){
return call_user_func([$this, "cache_get_{$this->CACHE_CHOSEN_PROGRAM}"], $key, $default);
}
public function cache_set($key, $data, $seconds = 8640000){
return call_user_func([$this, "cache_set_{$this->CACHE_CHOSEN_PROGRAM}"], $key, $data, $seconds);
}
public function cache_append($key, $data, $seconds = 8640000){
$existing_arr = call_user_func([$this, "cache_get_{$this->CACHE_CHOSEN_PROGRAM}"], $key, []);
$new = $this->is_array($existing_arr) ? $this->array_merge($existing_arr,$data) : $existing_arr. $data;
$final_value = ($this->is_simple_type($new) ? $new : serialize($new));
return call_user_func([$this, "cache_set_{$this->CACHE_CHOSEN_PROGRAM}"], $key, $final_value, $seconds);
}
#region ### phpRedis (better than "pRedis" ) [edit: 02mxypZ1 ] ###
public $redis_host_params = [
'host' => '127.0.0.1',
'port' => 6379,
'connectTimeout' => 2.5,
'db_index' => 0,
'auth' => ['', ''],
'ssl' => ['verify_peer' => false],
];
public $redis_keys_prefix='';
public $redis_instance = null;
public $redis_default_key_pre = ':';
public function cache_get_redis($key, $default=null){
$this->helper_cache_redis_init_check($this->redis_host_params, true);
$key = $this->redis_keys_prefix . $key;
$redis = $this->helper_redis_getInstance();
$val = $redis->get($key);
$this->helper_redis_IfSwooleCloseNeeded($redis);
if (!$val)
return $default;
return (self::is_serialized($val) ? unserialize($val) : $val);
}
public function cache_set_redis($key, $data, $seconds = 8640000){
$this->helper_cache_redis_init_check($this->redis_host_params, true);
$key = $this->redis_keys_prefix . $key;
$redis =$this->helper_redis_getInstance();
$result = $redis->set($key, ($this->is_simple_type($data) ? $data : serialize($data)), $seconds );
$this->helper_redis_IfSwooleCloseNeeded($redis);
return $result;
}
// public function cache_append_redis($key, $data, $seconds = 8640000){
// $this->helper_cache_redis_init($this->redis_host);
// $existing_arr = $this->cache_get_redis($key,[]);
// $new = $this->is_array($existing_arr) ? $this->array_merge($existing_arr,$data) : $existing_arr. $data;
// $final_value = ($this->is_simple_type($new) ? $new : serialize($new));
// return $this->cache_set_redis($key, $final_value, $seconds);
// }
public function cache_clear_redis(){
$this->helper_cache_redis_init_check($this->redis_host_params, true);
$this->helper_redis_getInstance()->flushAll();
}
// helpers, with added swoole support
private $redis_pool=null; private $redis_start_inited=false;
public function helper_cache_redis_init($host_params, $use_params=false){
try{
if (self::swoole_inside_coroutine()){
if ( is_null($this->redis_pool) ){
$authString = !empty($host_params['auth'][0]) ? $host_params['auth'][0].':'.$host_params['auth'][1] : '';
$newR = (new \Swoole\Database\RedisConfig)->withHost($host_params['host'])->withPort($host_params['port'])->withAuth($authString)->withDbIndex($host_params['db_index'])->withTimeout($host_params['connectTimeout']);
$this->redis_pool = new \Swoole\Database\RedisPool( $newR );
$this->redis_instance= $this->helper_redis_getInstance();
}
}
else {
if ( is_null($this->redis_instance) ){
$this->redis_instance= new \Redis();
$this->redis_instance->connect( $host_params['host'], $host_params['port']);
if ($use_params)
{
// SERIALIZER_NONE | SERIALIZER_PHP | SERIALIZER_IGBINARY | SERIALIZER_MSGPACK );
$this->redis_instance->setOption(\Redis::OPT_SERIALIZER, \Redis::SERIALIZER_PHP);
$this->redis_instance->setOption(\Redis::OPT_PREFIX, __NAMESPACE__. $this->redis_default_key_pre); // use custom prefix on all keys
}
}
}
if ($use_params)
$this->redis_keys_prefix = $this->slug .'_';
}
catch(\Exception $ex){
if (get_class($ex)==="RedisException"){
if (!$this->redis_start_inited){
$this->redis_start_inited=true;
if(method_exists($this,'helper_redis_try_os_start')) $this->helper_redis_try_os_start();
sleep(1);
$this->helper_cache_redis_init($host_params);
}
}
}
}
public function helper_cache_redis_init_check($host_params, $use_params=false){
if(is_null($this->redis_instance))
$this->helper_cache_redis_init($host_params, $use_params);
}
public function helper_redis_getInstance()
{
return (self::swoole_inside_coroutine() ? $this->redis_pool->get() : $this->redis_instance);
}
public function helper_redis_getAllKeys($redis_instance)
{
$keys=[];
$it = NULL;
do {
$arr_keys = $redis_instance->scan($it);
if ($arr_keys !== FALSE) {
foreach($arr_keys as $str_key) {
$keys[]= $str_key;
}
}
} while ($it > 0);
return $keys;
}
public function helper_redis_IfSwooleCloseNeeded($redis_instance)
{
if ( self::swoole_inside_coroutine() ){
$this->redis_pool->put($redis_instance);
}
}
#endregion
// ##### memcached: todo #####
//
//
//
//
//
//
// ##### apcu: todo ##### (examples: https://pastebin_com/0Q5y28fA)
//
//
//
//
//
//
// ####################### OBJECTS ####################### //
// https://medium.com/@dylanwenzlau/500x-faster-caching-than-redis-memcache-apc-in-php-hhvm-dcd26e8447ad
// sample ---> https://pastebin_com/0eUvyXaD
public $cache_object_method='serialize'; //serialize | memcached | apcu
public function cache_get_object($uniqFileName, $default='', $expire_seconds=86400 )
{
if ($this->cache_object_method=='apcu')
{
}
else{
$data = $this->cache_get_file($uniqFileName, $default, $expire_seconds, $decode=false);
return unserialize( $data );
}
}
public function cache_set_object($uniqFileName, $content, $throw_exception=true)
{
$res=false;
if ($this->cache_object_method=='apcu')
{
}
else{
$res = $this->cache_set_file($uniqFileName, serialize($content), false);
}
if(!$res && $throw_exception){
throw new \Exception('Was unable to set APCU cache for '.$uniqFileName);
}
return $res;
}
// ### CACHE DIRS ###
private $cacheDirectory = __DIR__.'/_cache/'; //sys_get_temp_dir()
public function cache_dir_set($dir=null, $auto_clear_seconds=null){
if($dir) $this->cacheDirectory = $dir;
$res = $this->mkdir($this->cacheDirectory);
if( !is_null($auto_clear_seconds))
{
$this->clearCacheDir($auto_clear_seconds);
}
return $res;
}
public function cache_dir_get($create=true){
$dir = $this->cacheDirectory;
if($create && !is_dir($dir)){ $this->mkdir($dir); }
return $dir;
}
// ### CACHE FILES ###
public function cache_file_location($uniqFileName){
$uniqFileName = is_string($uniqFileName) || is_numeric($uniqFileName) ? $uniqFileName : json_encode($uniqFileName);
$uniqFileName = self::sanitize( substr($uniqFileName, 0, 10)) . "_" . md5($uniqFileName);
$filePath= $this->cache_dir_get() . $uniqFileName ."_tmp"; //"/".
return $this->realpath($filePath);
}
public function cache_get_file($uniqFileName, $default='', $expire_seconds=8640000)
{
$filePath= $this->cache_file_location($uniqFileName);
if ( strlen($filePath) < 3) return "too tiny filename";
if ( file_exists($filePath) ){
if (filemtime($filePath)+$expire_seconds