forked from lolcat/4get
		
	
		
			
				
	
	
		
			282 lines
		
	
	
		
			6.0 KiB
		
	
	
	
		
			PHP
		
	
	
	
	
	
			
		
		
	
	
			282 lines
		
	
	
		
			6.0 KiB
		
	
	
	
		
			PHP
		
	
	
	
	
	
<?php
 | 
						|
 | 
						|
class bot_protection{
 | 
						|
	
 | 
						|
	public function __construct($frontend, $get, $filters, $page, $output){
 | 
						|
		
 | 
						|
		// check if we want captcha
 | 
						|
		if(config::BOT_PROTECTION !== 1){
 | 
						|
			
 | 
						|
			apcu_inc("real_requests");
 | 
						|
			if($output === true){
 | 
						|
				$frontend->loadheader(
 | 
						|
					$get,
 | 
						|
					$filters,
 | 
						|
					$page
 | 
						|
				);
 | 
						|
			}
 | 
						|
			return;
 | 
						|
		}
 | 
						|
		
 | 
						|
		/*
 | 
						|
			Validate cookie, if it exists
 | 
						|
		*/
 | 
						|
		if(isset($_COOKIE["pass"])){
 | 
						|
			
 | 
						|
			if(
 | 
						|
				// check if key is not malformed
 | 
						|
				preg_match(
 | 
						|
					'/^k[0-9]+\.[A-Za-z0-9_]{20}$/',
 | 
						|
					$_COOKIE["pass"]
 | 
						|
				) &&
 | 
						|
				// does key exist
 | 
						|
				apcu_exists($_COOKIE["pass"])
 | 
						|
			){
 | 
						|
					
 | 
						|
				// exists, increment counter
 | 
						|
				$inc = apcu_inc($_COOKIE["pass"]);
 | 
						|
				
 | 
						|
				// we start counting from 1
 | 
						|
				// when it has been incremented to 102, it has reached
 | 
						|
				// 100 reqs
 | 
						|
				if($inc >= config::MAX_SEARCHES + 2){
 | 
						|
					
 | 
						|
					// reached limit, delete and give captcha
 | 
						|
					apcu_delete($_COOKIE["pass"]);
 | 
						|
				}else{
 | 
						|
					
 | 
						|
					// the cookie is OK! dont die() and give results
 | 
						|
					apcu_inc("real_requests");
 | 
						|
					
 | 
						|
					if($output === true){
 | 
						|
						$frontend->loadheader(
 | 
						|
							$get,
 | 
						|
							$filters,
 | 
						|
							$page
 | 
						|
						);
 | 
						|
					}
 | 
						|
					return;
 | 
						|
				}
 | 
						|
			}
 | 
						|
		}
 | 
						|
		
 | 
						|
		if($output === false){
 | 
						|
			
 | 
						|
			http_response_code(401); // forbidden
 | 
						|
			echo json_encode([
 | 
						|
				"status" => "The \"pass\" token in your cookies is missing or has expired!!"
 | 
						|
			]);
 | 
						|
			die();
 | 
						|
		}
 | 
						|
		
 | 
						|
		/*
 | 
						|
			Validate form data
 | 
						|
		*/
 | 
						|
		$lines =
 | 
						|
			explode(
 | 
						|
				"\r\n",
 | 
						|
				file_get_contents("php://input")
 | 
						|
			);
 | 
						|
 | 
						|
		$invalid = false;
 | 
						|
		$answers = [];
 | 
						|
		$key = false;
 | 
						|
		$error = "";
 | 
						|
 | 
						|
		foreach($lines as $line){
 | 
						|
			
 | 
						|
			$line = explode("=", $line, 2);
 | 
						|
			
 | 
						|
			if(count($line) !== 2){
 | 
						|
				
 | 
						|
				$invalid = true;
 | 
						|
				break;
 | 
						|
			}
 | 
						|
			
 | 
						|
			preg_match(
 | 
						|
				'/^c\[([0-9]+)\]$/',
 | 
						|
				$line[0],
 | 
						|
				$regex
 | 
						|
			);
 | 
						|
			
 | 
						|
			if(
 | 
						|
				$line[1] != "on" ||
 | 
						|
				!isset($regex[0][1])
 | 
						|
			){
 | 
						|
				
 | 
						|
				// check if its the v key
 | 
						|
				if(
 | 
						|
					$line[0] == "v" &&
 | 
						|
					preg_match(
 | 
						|
						'/^c[0-9]+\.[A-Za-z0-9_]{20}$/',
 | 
						|
						$line[1]
 | 
						|
					)
 | 
						|
				){
 | 
						|
					
 | 
						|
					$key = apcu_fetch($line[1]);
 | 
						|
					apcu_delete($line[1]);
 | 
						|
				}
 | 
						|
				break;
 | 
						|
			}
 | 
						|
			
 | 
						|
			$regex = (int)$regex[1];
 | 
						|
			
 | 
						|
			if(
 | 
						|
				$regex >= 16 ||
 | 
						|
				$regex <= -1
 | 
						|
			){
 | 
						|
				
 | 
						|
				$invalid = true;
 | 
						|
				break;
 | 
						|
			}
 | 
						|
			
 | 
						|
			$answers[] = $regex;
 | 
						|
		}
 | 
						|
		
 | 
						|
		if(
 | 
						|
			!$invalid &&
 | 
						|
			$key !== false // has captcha been gen'd?
 | 
						|
		){
 | 
						|
			$check = count($key);
 | 
						|
			
 | 
						|
			// validate answer
 | 
						|
			for($i=0; $i<count($answers); $i++){
 | 
						|
				
 | 
						|
				if(in_array($answers[$i], $key)){
 | 
						|
					
 | 
						|
					$check--;
 | 
						|
				}else{
 | 
						|
					
 | 
						|
					$check = -1;
 | 
						|
					break;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			
 | 
						|
			if($check === 0){
 | 
						|
				
 | 
						|
				// we passed the captcha
 | 
						|
				// set cookie
 | 
						|
				$inc = apcu_inc("cookie");
 | 
						|
				
 | 
						|
				$key = "k" . $inc . "." . $this->randomchars();
 | 
						|
				
 | 
						|
				apcu_inc($key, 1, $stupid, 86400);
 | 
						|
				
 | 
						|
				apcu_inc("real_requests");
 | 
						|
				
 | 
						|
				setcookie(
 | 
						|
					"pass",
 | 
						|
					$key,
 | 
						|
					[
 | 
						|
						"expires" => time() + 86400, // expires in 24 hours
 | 
						|
						"samesite" => "Lax",
 | 
						|
						"path" => "/"
 | 
						|
					]
 | 
						|
				);
 | 
						|
				
 | 
						|
				$frontend->loadheader(
 | 
						|
					$get,
 | 
						|
					$filters,
 | 
						|
					$page
 | 
						|
				);
 | 
						|
				return;
 | 
						|
				
 | 
						|
			}else{
 | 
						|
				
 | 
						|
				$error = "<div class=\"quote\">You were <a href=\"https://www.youtube.com/watch?v=e1d7fkQx2rk\" target=\"_BLANK\" rel=\"noreferrer nofollow\">kicked out of Mensa.</a> Please try again.</div>";
 | 
						|
			}
 | 
						|
		}
 | 
						|
		
 | 
						|
		$key = "c" . apcu_inc("captcha_gen", 1) . "." . $this->randomchars();
 | 
						|
		
 | 
						|
		$payload = [
 | 
						|
			"timetaken" => microtime(true),
 | 
						|
			"class" => "",
 | 
						|
			"right-left" => "",
 | 
						|
			"right-right" => "",
 | 
						|
			"left" =>
 | 
						|
				'<div class="infobox">' .
 | 
						|
					'<h1>IQ test</h1>' .
 | 
						|
					'IQ test has been enabled due to bot abuse on the network.<br>' .
 | 
						|
					'Solving this IQ test will let you make 100 searches today. I will add an invite system to bypass this soon...' .
 | 
						|
					$error .
 | 
						|
					'<form method="POST" enctype="text/plain" autocomplete="off">' .
 | 
						|
						'<div class="captcha-wrapper">' .
 | 
						|
							'<div class="captcha">' .
 | 
						|
								'<img src="captcha?v=' . $key . '" alt="Captcha image">' .
 | 
						|
								'<div class="captcha-controls">' .
 | 
						|
									'<input type="checkbox" name="c[0]" id="c0">' .
 | 
						|
									'<label for="c0"></label>' .
 | 
						|
									'<input type="checkbox" name="c[1]" id="c1">' .
 | 
						|
									'<label for="c1"></label>' .
 | 
						|
									'<input type="checkbox" name="c[2]" id="c2">' .
 | 
						|
									'<label for="c2"></label>' .
 | 
						|
									'<input type="checkbox" name="c[3]" id="c3">' .
 | 
						|
									'<label for="c3"></label>' .
 | 
						|
									'<input type="checkbox" name="c[4]" id="c4">' .
 | 
						|
									'<label for="c4"></label>' .
 | 
						|
									'<input type="checkbox" name="c[5]" id="c5">' .
 | 
						|
									'<label for="c5"></label>' .
 | 
						|
									'<input type="checkbox" name="c[6]" id="c6">' .
 | 
						|
									'<label for="c6"></label>' .
 | 
						|
									'<input type="checkbox" name="c[7]" id="c7">' .
 | 
						|
									'<label for="c7"></label>' .
 | 
						|
									'<input type="checkbox" name="c[8]" id="c8">' .
 | 
						|
									'<label for="c8"></label>' .
 | 
						|
									'<input type="checkbox" name="c[9]" id="c9">' .
 | 
						|
									'<label for="c9"></label>' .
 | 
						|
									'<input type="checkbox" name="c[10]" id="c10">' .
 | 
						|
									'<label for="c10"></label>' .
 | 
						|
									'<input type="checkbox" name="c[11]" id="c11">' .
 | 
						|
									'<label for="c11"></label>' .
 | 
						|
									'<input type="checkbox" name="c[12]" id="c12">' .
 | 
						|
									'<label for="c12"></label>' .
 | 
						|
									'<input type="checkbox" name="c[13]" id="c13">' .
 | 
						|
									'<label for="c13"></label>' .
 | 
						|
									'<input type="checkbox" name="c[14]" id="c14">' .
 | 
						|
									'<label for="c14"></label>' .
 | 
						|
									'<input type="checkbox" name="c[15]" id="c15">' .
 | 
						|
									'<label for="c15"></label>' .
 | 
						|
								'</div>' .
 | 
						|
							'</div>' .
 | 
						|
						'</div>' .
 | 
						|
						'<input type="hidden" name="v" value="' . $key . '">' .
 | 
						|
						'<input type="submit" value="Check IQ" class="captcha-submit">' .
 | 
						|
					'</form>' .
 | 
						|
				'</div>'
 | 
						|
		];
 | 
						|
		
 | 
						|
		$frontend->loadheader(
 | 
						|
			$get,
 | 
						|
			$filters,
 | 
						|
			$page
 | 
						|
		);
 | 
						|
		
 | 
						|
		echo $frontend->load("search.html", $payload);
 | 
						|
		die();
 | 
						|
	}
 | 
						|
	
 | 
						|
	private function randomchars(){
 | 
						|
		
 | 
						|
		$chars =
 | 
						|
			array_merge(
 | 
						|
				range("A", "Z"),
 | 
						|
				range("a", "z"),
 | 
						|
				range(0, 9)
 | 
						|
			);
 | 
						|
		
 | 
						|
		$chars[] = "_";
 | 
						|
		
 | 
						|
		$c = count($chars) - 1;
 | 
						|
		
 | 
						|
		$key = "";
 | 
						|
		
 | 
						|
		for($i=0; $i<20; $i++){
 | 
						|
			
 | 
						|
			$key .= $chars[random_int(0, $c)];
 | 
						|
		}
 | 
						|
		
 | 
						|
		return $key;
 | 
						|
	}
 | 
						|
}
 |