1<?php
2// This session is part of Moodle - http://moodle.org/
3//
4// Moodle is free software: you can redistribute it and/or modify
5// it under the terms of the GNU General Public License as published by
6// the Free Software Foundation, either version 3 of the License, or
7// (at your option) any later version.
8//
9// Moodle is distributed in the hope that it will be useful,
10// but WITHOUT ANY WARRANTY; without even the implied warranty of
11// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12// GNU General Public License for more details.
13//
14// You should have received a copy of the GNU General Public License
15// along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
16
17/**
18 * Session unit tests
19 *
20 * @package    cachestore_session
21 * @copyright  2013 Sam Hemelryk
22 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
23 */
24
25defined('MOODLE_INTERNAL') || die();
26
27// Include the necessary evils.
28global $CFG;
29require_once($CFG->dirroot.'/cache/tests/fixtures/stores.php');
30require_once($CFG->dirroot.'/cache/stores/session/lib.php');
31
32/**
33 * Session unit test class.
34 *
35 * @package    cachestore_session
36 * @copyright  2013 Sam Hemelryk
37 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
38 */
39class cachestore_session_test extends cachestore_tests {
40    /**
41     * Returns the session class name
42     * @return string
43     */
44    protected function get_class_name() {
45        return 'cachestore_session';
46    }
47
48    /**
49     * Test the maxsize option.
50     */
51    public function test_maxsize() {
52        $config = cache_config_testing::instance();
53        $config->phpunit_add_definition('phpunit/one', array(
54            'mode' => cache_store::MODE_SESSION,
55            'component' => 'phpunit',
56            'area' => 'one',
57            'maxsize' => 3
58        ));
59
60        $config->phpunit_add_definition('phpunit/two', array(
61            'mode' => cache_store::MODE_SESSION,
62            'component' => 'phpunit',
63            'area' => 'two',
64            'maxsize' => 3
65        ));
66
67        $cacheone = cache::make('phpunit', 'one');
68
69        $this->assertTrue($cacheone->set('key1', 'value1'));
70        $this->assertTrue($cacheone->set('key2', 'value2'));
71        $this->assertTrue($cacheone->set('key3', 'value3'));
72
73        $this->assertTrue($cacheone->has('key1'));
74        $this->assertTrue($cacheone->has('key2'));
75        $this->assertTrue($cacheone->has('key3'));
76
77        $this->assertTrue($cacheone->set('key4', 'value4'));
78        $this->assertTrue($cacheone->set('key5', 'value5'));
79
80        $this->assertFalse($cacheone->has('key1'));
81        $this->assertFalse($cacheone->has('key2'));
82        $this->assertTrue($cacheone->has('key3'));
83        $this->assertTrue($cacheone->has('key4'));
84        $this->assertTrue($cacheone->has('key5'));
85
86        $this->assertFalse($cacheone->get('key1'));
87        $this->assertFalse($cacheone->get('key2'));
88        $this->assertEquals('value3', $cacheone->get('key3'));
89        $this->assertEquals('value4', $cacheone->get('key4'));
90        $this->assertEquals('value5', $cacheone->get('key5'));
91
92        // Test adding one more.
93        $this->assertTrue($cacheone->set('key6', 'value6'));
94        $this->assertFalse($cacheone->get('key3'));
95
96        // Test reducing and then adding to make sure we don't lost one.
97        $this->assertTrue($cacheone->delete('key6'));
98        $this->assertTrue($cacheone->set('key7', 'value7'));
99        $this->assertEquals('value4', $cacheone->get('key4'));
100
101        // Set the same key three times to make sure it doesn't count overrides.
102        for ($i = 0; $i < 3; $i++) {
103            $this->assertTrue($cacheone->set('key8', 'value8'));
104        }
105        $this->assertEquals('value7', $cacheone->get('key7'), 'Overrides are incorrectly incrementing size');
106
107        // Test adding many.
108        $this->assertEquals(3, $cacheone->set_many(array(
109            'keyA' => 'valueA',
110            'keyB' => 'valueB',
111            'keyC' => 'valueC'
112        )));
113        $this->assertEquals(array(
114            'key4' => false,
115            'key5' => false,
116            'key6' => false,
117            'key7' => false,
118            'keyA' => 'valueA',
119            'keyB' => 'valueB',
120            'keyC' => 'valueC'
121        ), $cacheone->get_many(array(
122            'key4', 'key5', 'key6', 'key7', 'keyA', 'keyB', 'keyC'
123        )));
124
125        $cachetwo = cache::make('phpunit', 'two');
126
127        // Test adding many.
128        $this->assertEquals(3, $cacheone->set_many(array(
129            'keyA' => 'valueA',
130            'keyB' => 'valueB',
131            'keyC' => 'valueC'
132        )));
133
134        $this->assertEquals(3, $cachetwo->set_many(array(
135            'key1' => 'value1',
136            'key2' => 'value2',
137            'key3' => 'value3'
138        )));
139
140        $this->assertEquals(array(
141            'keyA' => 'valueA',
142            'keyB' => 'valueB',
143            'keyC' => 'valueC'
144        ), $cacheone->get_many(array(
145            'keyA', 'keyB', 'keyC'
146        )));
147
148        $this->assertEquals(array(
149            'key1' => 'value1',
150            'key2' => 'value2',
151            'key3' => 'value3'
152        ), $cachetwo->get_many(array(
153            'key1', 'key2', 'key3'
154        )));
155
156        // Test that that cache deletes element that was least recently accessed.
157        $this->assertEquals('valueA', $cacheone->get('keyA'));
158        $cacheone->set('keyD', 'valueD');
159        $this->assertEquals('valueA', $cacheone->get('keyA'));
160        $this->assertFalse($cacheone->get('keyB'));
161        $this->assertEquals(array('keyD' => 'valueD', 'keyC' => 'valueC'), $cacheone->get_many(array('keyD', 'keyC')));
162        $cacheone->set('keyE', 'valueE');
163        $this->assertFalse($cacheone->get('keyB'));
164        $this->assertFalse($cacheone->get('keyA'));
165        $this->assertEquals(array('keyA' => false, 'keyE' => 'valueE', 'keyD' => 'valueD', 'keyC' => 'valueC'),
166                $cacheone->get_many(array('keyA', 'keyE', 'keyD', 'keyC')));
167        // Overwrite keyE (moves it to the end of array), and set keyF.
168        $cacheone->set_many(array('keyE' => 'valueE', 'keyF' => 'valueF'));
169        $this->assertEquals(array('keyC' => 'valueC', 'keyE' => 'valueE', 'keyD' => false, 'keyF' => 'valueF'),
170                $cacheone->get_many(array('keyC', 'keyE', 'keyD', 'keyF')));
171    }
172
173    public function test_ttl() {
174        $config = cache_config_testing::instance();
175        $config->phpunit_add_definition('phpunit/three', array(
176            'mode' => cache_store::MODE_SESSION,
177            'component' => 'phpunit',
178            'area' => 'three',
179            'maxsize' => 3,
180            'ttl' => 3
181        ));
182
183        $cachethree = cache::make('phpunit', 'three');
184
185        // Make sure that when cache with ttl is full the elements that were added first are deleted first regardless of access time.
186        $cachethree->set('key1', 'value1');
187        $cachethree->set('key2', 'value2');
188        $cachethree->set('key3', 'value3');
189        $cachethree->set('key4', 'value4');
190        $this->assertFalse($cachethree->get('key1'));
191        $this->assertEquals('value4', $cachethree->get('key4'));
192        $cachethree->set('key5', 'value5');
193        $this->assertFalse($cachethree->get('key2'));
194        $this->assertEquals('value4', $cachethree->get('key4'));
195        $cachethree->set_many(array('key6' => 'value6', 'key7' => 'value7'));
196        $this->assertEquals(array('key3' => false, 'key4' => false, 'key5' => 'value5', 'key6' => 'value6', 'key7' => 'value7'),
197                $cachethree->get_many(array('key3', 'key4', 'key5', 'key6', 'key7')));
198    }
199}