1<?php23declare(strict_types=1);45namespaceApp\Http\Middleware;67useClosure;8useGuzzleHttp\Clientas Guzzle;9useGuzzleHttp\Exception\GuzzleException;10useIlluminate\Http\Request;11useSymfony\Component\HttpKernel\Exception\AccessDeniedHttpException;1213classAcceptOnlyGitHubHooksIpAddrs14{15/**
16 * @paramGuzzle17 */18protected$guzzle;1920/**
21 * AcceptOnlyGitHubIpAddrs constructor.
22 */23publicfunction__construct(Guzzle$guzzle)24{25$this->guzzle=$guzzle;26}2728/**
29 * Handles request.
30 *
31 * @paramRequest$request32 * @paramClosure$next33 * @returnmixed34 * @throwsAccessDeniedHttpException35 */36publicfunctionhandle(Request$request,Closure$next)37{38if(!$this->ipInRanges((string)$request->ip(),$this->possibleIpRanges())){39thrownewAccessDeniedHttpException();40}41return$next($request);42}4344/**
45 * Fetch possible IP ranges from GitHub API.
46 *
47 * @returnstring[]48 * @throwsGuzzleException49 */50protectedfunctionpossibleIpRanges():array51{52returnjson_decode((string)$this->guzzle->get('https://api.github.com/meta')->getBody())->hooks??[];53}5455/**
56 * Check if a given ip is in networks.
57 *
58 * @paramstring$ip59 * @paramstring[]$ranges60 * @returnbool61 */62protectedfunctionipInRanges(string$ip,array$ranges):bool63{64foreach($rangesas$range){65if($this->ipInRange($ip,$range)){66returntrue;67}68}69returnfalse;70}7172/**
73 * Check if a given ip is in a network.
74 *
75 * @paramstring$ip IP to check in IPV4 format eg. 127.0.0.1
76 * @paramstring$range IP/CIDR netmask eg. 127.0.0.0/24, also 127.0.0.1 is accepted and /32 assumed
77 * @returnbool true if the ip is in this range / false if not.
78 */79protectedfunctionipInRange(string$ip,string$range):bool80{81if(strpos($range,'/')===false){82$range.='/32';83}8485[$range,$netmask]=explode('/',$range,2);8687$ipDecimal=ip2long($ip);88$rangeDecimal=ip2long($range);8990return$ipDecimal!==false&&$rangeDecimal!==false&&ctype_digit($netmask)91?$this->ipInRangeDecimal($ipDecimal,$rangeDecimal,(int)$netmask)92:false;93}9495/**
96 * @paramint$ip97 * @paramint$range98 * @paramint$netmask99 * @returnbool100 */101protectedfunctionipInRangeDecimal(int$ip,int$range,int$netmask):bool102{103$netmask=~(2**(32-$netmask)-1);104return($ip&$netmask)===($range&$netmask);105}106}
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2019/03/27 18:59
2019/03/27 19:33