/** * 执行外部请求,并返回接口 * * $request->execute(); * * @param Request $request * @param Response $response * @return Response * @throws Exception */ public function executeRequest(Request $request, Response $response) { $previous = Request::$current; Request::$current = $request; // 如果post数据了 if ($post = $request->post()) { $request->body = http_build_query($post, null, '&'); $request->headers('content-type', 'application/x-www-form-urlencoded; charset=' . $request->charset); } // 如果需要暴露框架信息 if (Base::$expose) { $request->headers('user-agent', Base::version()); } try { // 处理header $sendHeaders = []; if ($headers = $request->headers()) { foreach ($headers as $key => $value) { if (is_array($value)) { $value = implode(', ', $value); } $sendHeaders[$key] = $value; } } // 处理cookie if ($cookies = $request->cookie()) { $sendHeaders['Cookie'] = http_build_query($cookies, null, '; '); } $url = $request->uri; if ($query = $request->query()) { $url .= '?' . http_build_query($query, null, '&'); } // 执行请求 $result = Requests::request($url, $sendHeaders, $request->body, $request->method, $this->options); if (!$result->success) { throw new RequestException('Error fetching remote :url [ status :code ]', [':url' => $url, ':code' => $result->status_code]); } foreach ($result->headers as $k => $v) { $response->headers($k, $v); } $response->status = $result->status_code; $response->body = $result->body; } catch (Exception $e) { Request::$current = $previous; throw $e; } Request::$current = $previous; return $response; }
/** * 跳转状态码的处理 * * @param Request $request * @param Response $response * @param RequestClient $client * @return null|Request */ public static function onHeaderLocation(Request $request, Response $response, RequestClient $client) { if ($client->follow && in_array($response->status, [Http::CREATED, Http::MOVED_PERMANENTLY, Http::FOUND, Http::SEE_OTHER, Http::TEMPORARY_REDIRECT])) { switch ($response->status) { default: case Http::MOVED_PERMANENTLY: case Http::TEMPORARY_REDIRECT: $followMethod = $request->method; break; case Http::CREATED: case Http::SEE_OTHER: $followMethod = Http::GET; break; case Http::FOUND: if ($client->strictRedirect) { $followMethod = $request->method; } else { $followMethod = Http::GET; } break; } $origHeaders = $request->headers(); $followHeaders = array_intersect_assoc($origHeaders, array_fill_keys($client->followHeaders, true)); $followRequest = Request::factory($response->headers('Location')); $followRequest->method = $followMethod; $followRequest->headers($followHeaders); if ($followMethod !== Http::GET) { $followRequest->body = $request->body; } return $followRequest; } return null; }