6 * Class CRM_Core_RegionTest
10 class ThemesTest
extends \CiviUnitTestCase
{
12 protected function setUp() {
13 $this->useTransaction();
17 public function getThemeExamples() {
20 // --- Library of example themes which we can include in tests. ---
24 'title' => 'Judy Garland',
26 'prefix' => 'tests/phpunit/Civi/Core/Theme/judy/',
27 'excludes' => ['test.extension.uitest-files/ignoreme.css'],
32 'title' => 'Liza Minnelli',
33 'prefix' => 'tests/phpunit/Civi/Core/Theme/liza/',
39 'title' => 'Blue Marine',
40 'url_callback' => [__CLASS__
, 'fakeCallback'],
46 'title' => 'Aqua Marine',
47 'url_callback' => [__CLASS__
, 'fakeCallback'],
49 'search_order' => ['aquamarine', 'bluemarine', '_fallback_'],
53 $civicrmBaseUrl = rtrim(\Civi
::paths()->getVariable('civicrm.root', 'url'), '/');
55 // --- Library of tests ---
57 // Use the default theme, Greenwich.
63 'civicrm-css/civicrm.css' => ["$civicrmBaseUrl/css/civicrm.css"],
64 'civicrm-css/joomla.css' => ["$civicrmBaseUrl/css/joomla.css"],
65 'test.extension.uitest-files/foo.css' => ["$civicrmBaseUrl/tests/extensions/test.extension.uitest/files/foo.css"],
69 // judy is defined. Let's use judy.
74 // Example theme to inspect
77 'civicrm-css/civicrm.css' => ["$civicrmBaseUrl/tests/phpunit/Civi/Core/Theme/judy/css/civicrm.css"],
78 'civicrm-css/joomla.css' => ["$civicrmBaseUrl/css/joomla.css"],
79 'test.extension.uitest-files/foo.css' => ["$civicrmBaseUrl/tests/extensions/test.extension.uitest/files/foo.css"],
81 'test.extension.uitest-files/ignoreme.css' => [],
85 // Misconfiguration: liza was previously used but then disappeared. Fallback to default, Greenwich.
91 'civicrm-css/civicrm.css' => ["$civicrmBaseUrl/css/civicrm.css"],
92 'civicrm-css/joomla.css' => ["$civicrmBaseUrl/css/joomla.css"],
93 'test.extension.uitest-files/foo.css' => ["$civicrmBaseUrl/tests/extensions/test.extension.uitest/files/foo.css"],
97 // We have some themes available, but the admin opted out.
103 'civicrm-css/civicrm.css' => [],
104 'civicrm-css/joomla.css' => ["$civicrmBaseUrl/css/joomla.css"],
105 'test.extension.uitest-files/foo.css' => ["$civicrmBaseUrl/tests/extensions/test.extension.uitest/files/foo.css"],
109 // Theme which overrides an extension's CSS file.
111 $hookJudy +
$hookLiza,
115 // Warning: If your local system has overrides for the `debug_enabled`, these results may vary.
116 'civicrm-css/civicrm.css' => ["$civicrmBaseUrl/tests/phpunit/Civi/Core/Theme/liza/css/civicrm.css"],
117 'civicrm-css/civicrm.min.css' => ["$civicrmBaseUrl/tests/phpunit/Civi/Core/Theme/liza/css/civicrm.min.css"],
118 'civicrm-css/joomla.css' => ["$civicrmBaseUrl/css/joomla.css"],
119 'test.extension.uitest-files/foo.css' => ["$civicrmBaseUrl/tests/phpunit/Civi/Core/Theme/liza/test.extension.uitest-files/foo.css"],
123 // Theme has a custom URL-lookup function.
125 $hookBlueMarine +
$hookAquaMarine,
129 'civicrm-css/civicrm.css' => ['http://example.com/blue/civicrm.css'],
130 'civicrm-css/joomla.css' => ["$civicrmBaseUrl/css/joomla.css"],
131 'test.extension.uitest-files/foo.css' => ['http://example.com/blue/foobar/foo.css'],
135 // Theme is derived from another.
137 $hookBlueMarine +
$hookAquaMarine,
141 'civicrm-css/civicrm.css' => ['http://example.com/aqua/civicrm.css'],
142 'civicrm-css/joomla.css' => ["$civicrmBaseUrl/css/joomla.css"],
143 'test.extension.uitest-files/foo.css' => ['http://example.com/blue/foobar/foo.css'],
153 * @param array $inputtedHook
154 * @param string $themeKey
155 * @param string $expectedTitle
156 * @param array $expectedUrls
157 * List of files to lookup plus the expected URLs.
158 * Array("{$extName}-{$fileName}" => "{$expectUrl}").
160 * @dataProvider getThemeExamples
162 public function testTheme($inputtedHook, $themeKey, $expectedTitle, $expectedUrls) {
163 $this->hookClass
->setHook('civicrm_themes', function (&$themes) use ($inputtedHook) {
164 foreach ($inputtedHook as $key => $value) {
165 $themes[$key] = $value;
169 \Civi
::settings()->set('theme_frontend', $themeKey);
170 \Civi
::settings()->set('theme_backend', $themeKey);
172 /** @var \Civi\Core\Themes $themeSvc */
173 $themeSvc = \Civi
::service('themes');
174 $theme = $themeSvc->get($themeSvc->getActiveThemeKey());
175 if ($expectedTitle) {
176 $this->assertEquals($expectedTitle, $theme['title']);
179 foreach ($expectedUrls as $inputFile => $expectedUrl) {
180 list ($ext, $file) = explode('-', $inputFile, 2);
181 $actualUrl = $themeSvc->resolveUrls($themeSvc->getActiveThemeKey(), $ext, $file);
182 foreach (array_keys($actualUrl) as $k) {
183 // Ignore cache revision key (`?r=abcd1234`).
184 list ($actualUrl[$k]) = explode('?', $actualUrl[$k], 2);
186 $this->assertEquals($expectedUrl, $actualUrl, "Check URL for $inputFile");
190 public static function fakeCallback($themes, $themeKey, $cssExt, $cssFile) {
191 $map['bluemarine']['civicrm']['css/bootstrap.css'] = ['http://example.com/blue/bootstrap.css'];
192 $map['bluemarine']['civicrm']['css/civicrm.css'] = ['http://example.com/blue/civicrm.css'];
193 $map['bluemarine']['test.extension.uitest']['files/foo.css'] = ['http://example.com/blue/foobar/foo.css'];
194 $map['aquamarine']['civicrm']['css/civicrm.css'] = ['http://example.com/aqua/civicrm.css'];
195 return $map[$themeKey][$cssExt][$cssFile] ?? Themes
::PASSTHRU
;
198 public function testGetAll() {
199 $all = \Civi
::service('themes')->getAll();
200 $this->assertTrue(isset($all['greenwich']));
201 $this->assertTrue(isset($all['_fallback_']));
204 public function testGetAvailable() {
205 $all = \Civi
::service('themes')->getAvailable();
206 $this->assertTrue(isset($all['greenwich']));
207 $this->assertFalse(isset($all['_fallback_']));
210 public function testApiOptions() {
211 $result = $this->callAPISuccess('Setting', 'getoptions', [
212 'field' => 'theme_backend',
214 $this->assertTrue(isset($result['values']['greenwich']));
215 $this->assertFalse(isset($result['values']['_fallback_']));