/** * {@inheritdoc} */ public function setCache($form_build_id, $form, $form_state) { // 6 hours cache life time for forms should be plenty. $expire = 21600; // Cache form structure. if (isset($form)) { if ($this->currentUser()->isAuthenticated()) { $form['#cache_token'] = $this->csrfToken->get(); } $this->keyValueExpirableFactory->get('form')->setWithExpire($form_build_id, $form, $expire); } // Cache form state. // Store the known list of safe strings for form re-use. // @todo Ensure we are not storing an excessively large string list in: // https://www.drupal.org/node/2295823 $form_state['build_info']['safe_strings'] = SafeMarkup::getAll(); if ($data = array_diff_key($form_state, array_flip($this->getUncacheableKeys()))) { $this->keyValueExpirableFactory->get('form_state')->setWithExpire($form_build_id, $data, $expire); } }
/** * {@inheritdoc} */ public function startTestSuite(\PHPUnit_Framework_TestSuite $suite) { // Use a static so we only do this test once after all the data providers // have run. static $tested = FALSE; if ($suite->getName() !== '' && !$tested) { $tested = TRUE; if (!empty(SafeMarkup::getAll())) { throw new \RuntimeException('SafeMarkup string list polluted by data providers'); } } }
/** * {@inheritdoc} */ public function setCache($form_build_id, $form, FormStateInterface $form_state) { // 6 hours cache life time for forms should be plenty. $expire = 21600; // Ensure that the form build_id embedded in the form structure is the same // as the one passed in as a parameter. This is an additional safety measure // to prevent legacy code operating directly with // \Drupal::formBuilder()->getCache() and \Drupal::formBuilder()->setCache() // from accidentally overwriting immutable form state. if (isset($form['#build_id']) && $form['#build_id'] != $form_build_id) { $this->logger->error('Form build-id mismatch detected while attempting to store a form in the cache.'); return; } // Cache form structure. if (isset($form)) { if ($this->currentUser->isAuthenticated()) { $form['#cache_token'] = $this->csrfToken->get(); } unset($form['#build_id_old']); $this->keyValueExpirableFactory->get('form')->setWithExpire($form_build_id, $form, $expire); } // Cache form state. if ($this->configFactory->get('system.performance')->get('cache.page.use_internal') && $this->isPageCacheable()) { $form_state->addBuildInfo('immutable', TRUE); } // Store the known list of safe strings for form re-use. // @todo Ensure we are not storing an excessively large string list in: // https://www.drupal.org/node/2295823 $form_state->addBuildInfo('safe_strings', SafeMarkup::getAll()); if ($data = $form_state->getCacheableArray()) { $this->keyValueExpirableFactory->get('form_state')->setWithExpire($form_build_id, $data, $expire); } }
/** * @covers ::loadCachedFormState */ public function testLoadCachedFormStateWithSafeStrings() { $this->assertEmpty(SafeMarkup::getAll()); $form_build_id = 'the_form_build_id'; $form_state = new FormState(); $cached_form = ['#cache_token' => NULL]; $this->formCacheStore->expects($this->once())->method('get')->with($form_build_id)->willReturn($cached_form); $this->account->expects($this->once())->method('isAnonymous')->willReturn(TRUE); $cached_form_state = ['build_info' => ['safe_strings' => ['a_safe_string' => ['html' => TRUE]]]]; $this->formStateCacheStore->expects($this->once())->method('get')->with($form_build_id)->willReturn($cached_form_state); $this->formCache->getCache($form_build_id, $form_state); }