BlockCacheTest.php 6.89 KB
Newer Older
1 2
<?php

3
namespace Drupal\Tests\block\Functional;
4

5
use Drupal\Core\Cache\Cache;
6
use Drupal\Tests\BrowserTestBase;
7 8

/**
9 10 11
 * Tests block caching.
 *
 * @group block
12
 */
13
class BlockCacheTest extends BrowserTestBase {
14 15

  /**
16
   * Modules to install.
17 18 19
   *
   * @var array
   */
20
  public static $modules = array('block', 'block_test', 'test_page_test');
21

22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41
  /**
   * A user with permission to create and edit books and to administer blocks.
   *
   * @var object
   */
  protected $adminUser;

  /**
   * An authenticated user to test block caching.
   *
   * @var object
   */
  protected $normalUser;

  /**
   * Another authenticated user to test block caching.
   *
   * @var object
   */
  protected $normalUserAlt;
42 43 44 45 46 47

  /**
   * The block used by this test.
   *
   * @var \Drupal\block\BlockInterface
   */
48
  protected $block;
49

50
  protected function setUp() {
51
    parent::setUp();
52 53

    // Create an admin user, log in and enable test blocks.
54 55
    $this->adminUser = $this->drupalCreateUser(array('administer blocks', 'access administration pages'));
    $this->drupalLogin($this->adminUser);
56 57

    // Create additional users to test caching modes.
58 59
    $this->normalUser = $this->drupalCreateUser();
    $this->normalUserAlt = $this->drupalCreateUser();
60 61
    // Sync the roles, since drupalCreateUser() creates separate roles for
    // the same permission sets.
62 63
    $this->normalUserAlt->roles = $this->normalUser->getRoles();
    $this->normalUserAlt->save();
64 65

    // Enable our test block.
66
    $this->block = $this->drupalPlaceBlock('test_cache');
67 68 69
  }

  /**
70
   * Test "user.roles" cache context.
71 72
   */
  function testCachePerRole() {
73
    \Drupal::state()->set('block_test.cache_contexts', ['user.roles']);
74 75

    // Enable our test block. Set some content for it to display.
76
    $current_content = $this->randomMachineName();
77
    \Drupal::state()->set('block_test.content', $current_content);
78
    $this->drupalLogin($this->normalUser);
79
    $this->drupalGet('');
80
    $this->assertText($current_content, 'Block content displays.');
81 82 83

    // Change the content, but the cached copy should still be served.
    $old_content = $current_content;
84
    $current_content = $this->randomMachineName();
85
    \Drupal::state()->set('block_test.content', $current_content);
86
    $this->drupalGet('');
87
    $this->assertText($old_content, 'Block is served from the cache.');
88 89

    // Clear the cache and verify that the stale data is no longer there.
90
    Cache::invalidateTags(array('block_view'));
91
    $this->drupalGet('');
92 93
    $this->assertNoText($old_content, 'Block cache clear removes stale cache data.');
    $this->assertText($current_content, 'Fresh block content is displayed after clearing the cache.');
94 95 96

    // Test whether the cached data is served for the correct users.
    $old_content = $current_content;
97
    $current_content = $this->randomMachineName();
98
    \Drupal::state()->set('block_test.content', $current_content);
99 100
    $this->drupalLogout();
    $this->drupalGet('');
101
    $this->assertNoText($old_content, 'Anonymous user does not see content cached per-role for normal user.');
102

103
    $this->drupalLogin($this->normalUserAlt);
104
    $this->drupalGet('');
105
    $this->assertText($old_content, 'User with the same roles sees per-role cached content.');
106

107
    $this->drupalLogin($this->adminUser);
108
    $this->drupalGet('');
109
    $this->assertNoText($old_content, 'Admin user does not see content cached per-role for normal user.');
110

111
    $this->drupalLogin($this->normalUser);
112
    $this->drupalGet('');
113
    $this->assertText($old_content, 'Block is served from the per-role cache.');
114 115 116
  }

  /**
117
   * Test a cacheable block without any additional cache context.
118
   */
119 120 121
  function testCachePermissions() {
    // user.permissions is a required context, so a user with different
    // permissions will see a different version of the block.
122
    \Drupal::state()->set('block_test.cache_contexts', []);
123

124
    $current_content = $this->randomMachineName();
125
    \Drupal::state()->set('block_test.content', $current_content);
126 127

    $this->drupalGet('');
128
    $this->assertText($current_content, 'Block content displays.');
129 130

    $old_content = $current_content;
131
    $current_content = $this->randomMachineName();
132
    \Drupal::state()->set('block_test.content', $current_content);
133 134

    $this->drupalGet('user');
135
    $this->assertText($old_content, 'Block content served from cache.');
136 137 138 139

    $this->drupalLogout();
    $this->drupalGet('user');
    $this->assertText($current_content, 'Block content not served from cache.');
140 141 142
  }

  /**
143
   * Test non-cacheable block.
144 145
   */
  function testNoCache() {
146
    \Drupal::state()->set('block_test.cache_max_age', 0);
147

148
    $current_content = $this->randomMachineName();
149
    \Drupal::state()->set('block_test.content', $current_content);
150

151
    // If max_age = 0 has no effect, the next request would be cached.
152
    $this->drupalGet('');
153
    $this->assertText($current_content, 'Block content displays.');
154 155

    // A cached copy should not be served.
156
    $current_content = $this->randomMachineName();
157
    \Drupal::state()->set('block_test.content', $current_content);
158
    $this->drupalGet('');
159
    $this->assertText($current_content, 'Maximum age of zero prevents blocks from being cached.');
160 161 162
  }

  /**
163
   * Test "user" cache context.
164 165
   */
  function testCachePerUser() {
166
    \Drupal::state()->set('block_test.cache_contexts', ['user']);
167

168
    $current_content = $this->randomMachineName();
169
    \Drupal::state()->set('block_test.content', $current_content);
170
    $this->drupalLogin($this->normalUser);
171 172

    $this->drupalGet('');
173
    $this->assertText($current_content, 'Block content displays.');
174 175

    $old_content = $current_content;
176
    $current_content = $this->randomMachineName();
177
    \Drupal::state()->set('block_test.content', $current_content);
178 179

    $this->drupalGet('');
180
    $this->assertText($old_content, 'Block is served from per-user cache.');
181

182
    $this->drupalLogin($this->normalUserAlt);
183
    $this->drupalGet('');
184
    $this->assertText($current_content, 'Per-user block cache is not served for other users.');
185

186
    $this->drupalLogin($this->normalUser);
187
    $this->drupalGet('');
188
    $this->assertText($old_content, 'Per-user block cache is persistent.');
189 190 191
  }

  /**
192
   * Test "url" cache context.
193 194
   */
  function testCachePerPage() {
195
    \Drupal::state()->set('block_test.cache_contexts', ['url']);
196

197
    $current_content = $this->randomMachineName();
198
    \Drupal::state()->set('block_test.content', $current_content);
199

200 201
    $this->drupalGet('test-page');
    $this->assertText($current_content, 'Block content displays on the test page.');
202 203

    $old_content = $current_content;
204
    $current_content = $this->randomMachineName();
205
    \Drupal::state()->set('block_test.content', $current_content);
206 207

    $this->drupalGet('user');
208 209 210 211 212
    $this->assertResponse(200);
    $this->assertNoText($old_content, 'Block content cached for the test page does not show up for the user page.');
    $this->drupalGet('test-page');
    $this->assertResponse(200);
    $this->assertText($old_content, 'Block content cached for the test page.');
213 214 215
  }

}