/** * Asserts that caching is allowed unless there is a session cookie present. * * @covers ::check */ public function testNoAllowUnlessSessionCookiePresent() { $request_without_session = new Request(); $request_with_session = Request::create('/', 'GET', [], ['some-session-name' => 'some-session-id']); $this->sessionConfiguration->expects($this->at(0))->method('hasSession')->with($request_without_session)->will($this->returnValue(FALSE)); $this->sessionConfiguration->expects($this->at(1))->method('hasSession')->with($request_with_session)->will($this->returnValue(TRUE)); $result = $this->policy->check($request_without_session); $this->assertSame(RequestPolicyInterface::ALLOW, $result); $result = $this->policy->check($request_with_session); $this->assertSame(NULL, $result); }
/** * {@inheritdoc} */ public function start() { if (($this->started || $this->startedLazy) && !$this->closed) { return $this->started; } $request = $this->requestStack->getCurrentRequest(); $this->setOptions($this->sessionConfiguration->getOptions($request)); if ($this->sessionConfiguration->hasSession($request)) { // If a session cookie exists, initialize the session. Otherwise the // session is only started on demand in save(), making // anonymous users not use a session cookie unless something is stored in // $_SESSION. This allows HTTP proxies to cache anonymous pageviews. $result = $this->startNow(); } if (empty($result)) { // Randomly generate a session identifier for this request. This is // necessary because \Drupal\user\SharedTempStoreFactory::get() wants to // know the future session ID of a lazily started session in advance. // // @todo: With current versions of PHP there is little reason to generate // the session id from within application code. Consider using the // default php session id instead of generating a custom one: // https://www.drupal.org/node/2238561 $this->setId(Crypt::randomBytesBase64()); // Initialize the session global and attach the Symfony session bags. $_SESSION = array(); $this->loadSession(); // NativeSessionStorage::loadSession() sets started to TRUE, reset it to // FALSE here. $this->started = FALSE; $this->startedLazy = TRUE; $result = FALSE; } return $result; }
/** * Checks access. * * @param \Symfony\Component\HttpFoundation\Request $request * The request object. * @param \Drupal\Core\Session\AccountInterface $account * The currently logged in account. * * @return \Drupal\Core\Access\AccessResultInterface * The access result. */ public function access(Request $request, AccountInterface $account) { $method = $request->getMethod(); // This check only applies if // 1. this is a write operation // 2. the user was successfully authenticated and // 3. the request comes with a session cookie. if (!in_array($method, array('GET', 'HEAD', 'OPTIONS', 'TRACE')) && $account->isAuthenticated() && $this->sessionConfiguration->hasSession($request)) { $csrf_token = $request->headers->get('X-CSRF-Token'); if (!\Drupal::csrfToken()->validate($csrf_token, 'rest')) { return AccessResult::forbidden()->setCacheMaxAge(0); } } // Let other access checkers decide if the request is legit. return AccessResult::allowed()->setCacheMaxAge(0); }
/** * {@inheritdoc} */ public function processPlaceholders(array $placeholders) { if (!$this->sessionConfiguration->hasSession($this->requestStack->getCurrentRequest())) { return []; } return $this->doProcessPlaceholders($placeholders); }
/** * {@inheritdoc} */ public function processPlaceholders(array $placeholders) { // Routes can opt out from using the BigPipe HTML delivery technique. if ($this->routeMatch->getRouteObject()->getOption('_no_big_pipe')) { return []; } if (!$this->sessionConfiguration->hasSession($this->requestStack->getCurrentRequest())) { return []; } return $this->doProcessPlaceholders($placeholders); }
/** * {@inheritdoc} */ public function processPlaceholders(array $placeholders) { $request = $this->requestStack->getCurrentRequest(); // @todo remove this check when https://www.drupal.org/node/2367555 lands. if (!$request->isMethodSafe()) { return []; } // Routes can opt out from using the BigPipe HTML delivery technique. if ($this->routeMatch->getRouteObject()->getOption('_no_big_pipe')) { return []; } if (!$this->sessionConfiguration->hasSession($request)) { return []; } return $this->doProcessPlaceholders($placeholders); }
/** * Checks access. * * @param \Symfony\Component\HttpFoundation\Request $request * The request object. * @param \Drupal\Core\Session\AccountInterface $account * The currently logged in account. * * @return \Drupal\Core\Access\AccessResultInterface * The access result. */ public function access(Request $request, AccountInterface $account) { $method = $request->getMethod(); // This check only applies if // 1. this is a write operation // 2. the user was successfully authenticated and // 3. the request comes with a session cookie. if (!in_array($method, array('GET', 'HEAD', 'OPTIONS', 'TRACE')) && $account->isAuthenticated() && $this->sessionConfiguration->hasSession($request)) { $csrf_token = $request->headers->get('X-CSRF-Token'); // @todo Remove validate call using 'rest' in 8.3. // Kept here for sessions active during update. if (!$this->csrfToken->validate($csrf_token, self::TOKEN_KEY) && !$this->csrfToken->validate($csrf_token, 'rest')) { return AccessResult::forbidden()->setReason('X-CSRF-Token request header is missing')->setCacheMaxAge(0); } } // Let other access checkers decide if the request is legit. return AccessResult::allowed()->setCacheMaxAge(0); }
/** * {@inheritdoc} */ public function applies(Request $request) { return $request->hasSession() && $this->sessionConfiguration->hasSession($request); }
/** * {@inheritdoc} */ public function check(Request $request) { if (!$this->sessionConfiguration->hasSession($request)) { return static::ALLOW; } }
/** * {@inheritdoc} */ public function getContext() { return $this->sessionConfiguration->hasSession($this->requestStack->getCurrentRequest()) ? '1' : '0'; }