PluginProbe ʕ •ᴥ•ʔ
Matomo Analytics – Powerful, Privacy-First Insights for WordPress / 1.3.1
Matomo Analytics – Powerful, Privacy-First Insights for WordPress v1.3.1
5.11.1 5.11.0 5.10.2 5.10.1 trunk 1.0.2 1.0.3 1.0.4 1.0.5 1.0.6 1.1.0 1.1.1 1.1.2 1.1.3 1.2.0 1.3.0 1.3.1 1.3.2 4.0.0 4.0.1 4.0.2 4.0.3 4.0.4 4.1.0 4.1.1 4.1.2 4.1.3 4.10.0 4.11.0 4.12.0 4.13.0 4.13.2 4.13.3 4.13.4 4.13.5 4.14.0 4.14.1 4.14.2 4.15.0 4.15.1 4.15.2 4.15.3 4.2.0 4.3.0 4.3.1 4.4.1 4.4.2 4.5.0 4.6.0 5.0.1 5.0.2 5.0.3 5.0.4 5.0.5 5.0.6 5.0.7 5.0.8 5.1.0 5.1.1 5.1.2 5.1.3 5.1.4 5.1.5 5.1.6 5.1.7 5.10.0 5.2.0 5.2.1 5.2.2 5.3.0 5.3.1 5.3.2 5.3.3 5.6.0 5.6.1 5.7.0 5.7.1 5.8.0 5.8.1 5.8.2
matomo / app / core / SettingsPiwik.php
matomo / app / core Last commit date
API 6 years ago Access 6 years ago Application 6 years ago Archive 6 years ago ArchiveProcessor 6 years ago Archiver 6 years ago AssetManager 6 years ago Auth 6 years ago Category 6 years ago CliMulti 6 years ago Columns 6 years ago Composer 6 years ago Concurrency 6 years ago Config 6 years ago Container 6 years ago CronArchive 6 years ago DataAccess 5 years ago DataFiles 6 years ago DataTable 6 years ago Db 6 years ago DeviceDetector 5 years ago Email 6 years ago Exception 6 years ago Http 6 years ago Intl 6 years ago Mail 6 years ago Measurable 6 years ago Menu 6 years ago Metrics 6 years ago Notification 6 years ago Period 6 years ago Plugin 6 years ago ProfessionalServices 6 years ago Report 6 years ago ReportRenderer 6 years ago Scheduler 6 years ago Segment 6 years ago Session 6 years ago Settings 6 years ago Tracker 5 years ago Translation 6 years ago UpdateCheck 6 years ago Updater 6 years ago Updates 6 years ago Validators 6 years ago View 6 years ago ViewDataTable 6 years ago Visualization 6 years ago Widget 6 years ago .htaccess 6 years ago Access.php 6 years ago Archive.php 6 years ago ArchiveProcessor.php 6 years ago AssetManager.php 6 years ago Auth.php 6 years ago BaseFactory.php 6 years ago Cache.php 6 years ago CacheId.php 6 years ago CliMulti.php 6 years ago Common.php 6 years ago Config.php 6 years ago Console.php 6 years ago Context.php 6 years ago Cookie.php 5 years ago CronArchive.php 5 years ago DataArray.php 6 years ago DataTable.php 6 years ago Date.php 6 years ago Db.php 6 years ago DbHelper.php 6 years ago Development.php 6 years ago DeviceDetectorFactory.php 6 years ago ErrorHandler.php 6 years ago EventDispatcher.php 6 years ago ExceptionHandler.php 6 years ago FileIntegrity.php 6 years ago Filechecks.php 6 years ago Filesystem.php 6 years ago FrontController.php 6 years ago Http.php 6 years ago IP.php 6 years ago Log.php 6 years ago LogDeleter.php 6 years ago Mail.php 6 years ago Metrics.php 6 years ago MetricsFormatter.php 6 years ago Nonce.php 5 years ago Notification.php 6 years ago NumberFormatter.php 6 years ago Option.php 5 years ago Period.php 6 years ago Piwik.php 6 years ago Plugin.php 6 years ago Profiler.php 6 years ago ProxyHeaders.php 6 years ago ProxyHttp.php 6 years ago QuickForm2.php 6 years ago RankingQuery.php 6 years ago Registry.php 6 years ago ReportRenderer.php 6 years ago ScheduledTask.php 6 years ago Segment.php 6 years ago Sequence.php 6 years ago Session.php 6 years ago SettingsPiwik.php 6 years ago SettingsServer.php 6 years ago Singleton.php 6 years ago Site.php 6 years ago TCPDF.php 6 years ago TaskScheduler.php 6 years ago Theme.php 6 years ago Timer.php 6 years ago Tracker.php 6 years ago Translate.php 6 years ago Twig.php 6 years ago Unzip.php 6 years ago UpdateCheck.php 6 years ago Updater.php 6 years ago Updates.php 6 years ago Url.php 6 years ago UrlHelper.php 6 years ago Version.php 5 years ago View.php 6 years ago bootstrap.php 6 years ago dispatch.php 6 years ago testMinimumPhpVersion.php 6 years ago
SettingsPiwik.php
527 lines
1 <?php
2 /**
3 * Piwik - free/libre analytics platform
4 *
5 * @link https://matomo.org
6 * @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
7 *
8 */
9 namespace Piwik;
10
11 use Exception;
12 use Piwik\Cache as PiwikCache;
13 use Piwik\Container\StaticContainer;
14
15 /**
16 * Contains helper methods that can be used to get common Piwik settings.
17 *
18 */
19 class SettingsPiwik
20 {
21 const OPTION_PIWIK_URL = 'piwikUrl';
22
23 /**
24 * Get salt from [General] section. Should ONLY be used as a seed to create hashes
25 *
26 * NOTE: Keep this salt secret! Never output anywhere or share it etc.
27 *
28 * @return string
29 */
30 public static function getSalt()
31 {
32 static $salt = null;
33 if (is_null($salt)) {
34 $salt = @Config::getInstance()->General['salt'];
35 }
36 return $salt;
37 }
38
39 /**
40 * Should Piwik check that the login & password have minimum length and valid characters?
41 *
42 * @return bool True if checks enabled; false otherwise
43 */
44 public static function isUserCredentialsSanityCheckEnabled()
45 {
46 return Config::getInstance()->General['disable_checks_usernames_attributes'] == 0;
47 }
48
49 /**
50 * Should Piwik show the update notification to superusers only?
51 *
52 * @return bool True if show to superusers only; false otherwise
53 */
54 public static function isShowUpdateNotificationToSuperUsersOnlyEnabled()
55 {
56 return Config::getInstance()->General['show_update_notification_to_superusers_only'] == 1;
57 }
58
59 /**
60 * Returns every stored segment to pre-process for each site during cron archiving.
61 *
62 * @return array The list of stored segments that apply to all sites.
63 */
64 public static function getKnownSegmentsToArchive()
65 {
66 $cacheId = 'KnownSegmentsToArchive';
67 $cache = PiwikCache::getTransientCache();
68 if ($cache->contains($cacheId)) {
69 return $cache->fetch($cacheId);
70 }
71
72 $segments = Config::getInstance()->Segments;
73 $segmentsToProcess = isset($segments['Segments']) ? $segments['Segments'] : array();
74
75 /**
76 * Triggered during the cron archiving process to collect segments that
77 * should be pre-processed for all websites. The archiving process will be launched
78 * for each of these segments when archiving data.
79 *
80 * This event can be used to add segments to be pre-processed. If your plugin depends
81 * on data from a specific segment, this event could be used to provide enhanced
82 * performance.
83 *
84 * _Note: If you just want to add a segment that is managed by the user, use the
85 * SegmentEditor API._
86 *
87 * **Example**
88 *
89 * Piwik::addAction('Segments.getKnownSegmentsToArchiveAllSites', function (&$segments) {
90 * $segments[] = 'country=jp;city=Tokyo';
91 * });
92 *
93 * @param array &$segmentsToProcess List of segment definitions, eg,
94 *
95 * array(
96 * 'browserCode=ff;resolution=800x600',
97 * 'country=jp;city=Tokyo'
98 * )
99 *
100 * Add segments to this array in your event handler.
101 */
102 Piwik::postEvent('Segments.getKnownSegmentsToArchiveAllSites', array(&$segmentsToProcess));
103
104 $segmentsToProcess = array_unique($segmentsToProcess);
105
106 $cache->save($cacheId, $segmentsToProcess);
107 return $segmentsToProcess;
108 }
109
110 /**
111 * Returns the list of stored segments to pre-process for an individual site when executing
112 * cron archiving.
113 *
114 * @param int $idSite The ID of the site to get stored segments for.
115 * @return string[] The list of stored segments that apply to the requested site.
116 */
117 public static function getKnownSegmentsToArchiveForSite($idSite)
118 {
119 $cacheId = 'KnownSegmentsToArchiveForSite' . $idSite;
120 $cache = PiwikCache::getTransientCache();
121 if ($cache->contains($cacheId)) {
122 return $cache->fetch($cacheId);
123 }
124
125 $segments = array();
126 /**
127 * Triggered during the cron archiving process to collect segments that
128 * should be pre-processed for one specific site. The archiving process will be launched
129 * for each of these segments when archiving data for that one site.
130 *
131 * This event can be used to add segments to be pre-processed for one site.
132 *
133 * _Note: If you just want to add a segment that is managed by the user, you should use the
134 * SegmentEditor API._
135 *
136 * **Example**
137 *
138 * Piwik::addAction('Segments.getKnownSegmentsToArchiveForSite', function (&$segments, $idSite) {
139 * $segments[] = 'country=jp;city=Tokyo';
140 * });
141 *
142 * @param array &$segmentsToProcess List of segment definitions, eg,
143 *
144 * array(
145 * 'browserCode=ff;resolution=800x600',
146 * 'country=JP;city=Tokyo'
147 * )
148 *
149 * Add segments to this array in your event handler.
150 * @param int $idSite The ID of the site to get segments for.
151 */
152 Piwik::postEvent('Segments.getKnownSegmentsToArchiveForSite', array(&$segments, $idSite));
153
154 $segments = array_unique($segments);
155
156 $cache->save($cacheId, $segments);
157
158 return $segments;
159 }
160
161 /**
162 * Number of websites to show in the Website selector
163 *
164 * @return int
165 */
166 public static function getWebsitesCountToDisplay()
167 {
168 $count = max(Config::getInstance()->General['site_selector_max_sites'],
169 Config::getInstance()->General['autocomplete_min_sites']);
170 return (int)$count;
171 }
172
173 /**
174 * Returns the URL to this Piwik instance, eg. **http://demo.piwik.org/** or **http://example.org/piwik/**.
175 *
176 * @return string
177 * @api
178 */
179 public static function getPiwikUrl()
180 {
181 $url = Option::get(self::OPTION_PIWIK_URL);
182
183 $isPiwikCoreDispatching = defined('PIWIK_ENABLE_DISPATCH') && PIWIK_ENABLE_DISPATCH;
184 if (Common::isPhpCliMode()
185 // in case core:archive command is triggered (often with localhost domain)
186 || SettingsServer::isArchivePhpTriggered()
187 // When someone else than core is dispatching this request then we return the URL as it is read only
188 || !$isPiwikCoreDispatching
189 ) {
190 return $url;
191 }
192
193 $currentUrl = Common::sanitizeInputValue(Url::getCurrentUrlWithoutFileName());
194
195 // when script is called from /misc/cron/archive.php, Piwik URL is /index.php
196 $currentUrl = str_replace("/misc/cron", "", $currentUrl);
197
198 if (empty($url)
199 // if URL changes, always update the cache
200 || $currentUrl != $url
201 ) {
202 $host = Url::getHostFromUrl($currentUrl);
203
204 if (strlen($currentUrl) >= strlen('http://a/')
205 && Url::isValidHost($host)
206 && !Url::isLocalHost($host)) {
207 self::overwritePiwikUrl($currentUrl);
208 }
209 $url = $currentUrl;
210 }
211
212 if (ProxyHttp::isHttps()) {
213 $url = str_replace("http://", "https://", $url);
214 }
215 return $url;
216 }
217
218 /**
219 * @see SettingsPiwik::isPiwikInstalled
220 * @return bool
221 */
222 public static function isMatomoInstalled()
223 {
224 return self::isPiwikInstalled();
225 }
226
227 /**
228 * Return true if Piwik is installed (installation is done).
229 * @deprecated since Matomo 3.8.0, please use {@link isMatomoInstalled()} instead.
230 * @return bool
231 */
232 public static function isPiwikInstalled()
233 {
234 $config = Config::getInstance()->getLocalPath();
235 $exists = file_exists($config);
236
237 // Piwik is not installed if the config file is not found
238 if (!$exists) {
239 return false;
240 }
241
242 $general = Config::getInstance()->General;
243
244 $isInstallationInProgress = false;
245 if (array_key_exists('installation_in_progress', $general)) {
246 $isInstallationInProgress = (bool) $general['installation_in_progress'];
247 }
248 if ($isInstallationInProgress) {
249 return false;
250 }
251
252 // Check that the database section is really set, ie. file is not empty
253 if (empty(Config::getInstance()->database['username'])) {
254 return false;
255 }
256 return true;
257 }
258
259 /**
260 * Check if outgoing internet connections are enabled
261 * This is often disable in an intranet environment
262 *
263 * @return bool
264 */
265 public static function isInternetEnabled()
266 {
267 return (bool) Config::getInstance()->General['enable_internet_features'];
268 }
269
270 /**
271 * Detect whether user has enabled auto updates. Please note this config is a bit misleading. It is currently
272 * actually used for 2 things: To disable making any connections back to Piwik, and to actually disable the auto
273 * update of core and plugins.
274 * @return bool
275 */
276 public static function isAutoUpdateEnabled()
277 {
278 $enableAutoUpdate = (bool) Config::getInstance()->General['enable_auto_update'];
279 if(self::isInternetEnabled() === true && $enableAutoUpdate === true){
280 return true;
281 }
282
283 return false;
284 }
285
286 /**
287 * Detects whether an auto update can be made. An update is possible if the user is not on multiple servers and if
288 * automatic updates are actually enabled. If a user is running Piwik on multiple servers an update is not possible
289 * as it would be installed only on one server instead of all of them. Also if a user has disabled automatic updates
290 * we cannot perform any automatic updates.
291 *
292 * @return bool
293 */
294 public static function isAutoUpdatePossible()
295 {
296 return !self::isMultiServerEnvironment() && self::isAutoUpdateEnabled();
297 }
298
299 /**
300 * Returns `true` if Piwik is running on more than one server. For example in a load balanced environment. In this
301 * case we should not make changes to the config and not install a plugin via the UI as it would be only executed
302 * on one server.
303 * @return bool
304 */
305 public static function isMultiServerEnvironment()
306 {
307 $is = Config::getInstance()->General['multi_server_environment'];
308
309 return !empty($is);
310 }
311
312 /**
313 * Returns `true` if segmentation is allowed for this user, `false` if otherwise.
314 *
315 * @return bool
316 * @api
317 */
318 public static function isSegmentationEnabled()
319 {
320 return !Piwik::isUserIsAnonymous()
321 || Config::getInstance()->General['anonymous_user_enable_use_segments_API'];
322 }
323
324 /**
325 * Returns true if unique visitors should be processed for the given period type.
326 *
327 * Unique visitor processing is controlled by the `[General] enable_processing_unique_visitors_...`
328 * INI config options. By default, unique visitors are processed only for day/week/month periods.
329 *
330 * @param string $periodLabel `"day"`, `"week"`, `"month"`, `"year"` or `"range"`
331 * @return bool
332 * @api
333 */
334 public static function isUniqueVisitorsEnabled($periodLabel)
335 {
336 $generalSettings = Config::getInstance()->General;
337
338 $settingName = "enable_processing_unique_visitors_$periodLabel";
339 $result = !empty($generalSettings[$settingName]) && $generalSettings[$settingName] == 1;
340
341 // check enable_processing_unique_visitors_year_and_range for backwards compatibility
342 if (($periodLabel == 'year' || $periodLabel == 'range')
343 && isset($generalSettings['enable_processing_unique_visitors_year_and_range'])
344 ) {
345 $result |= $generalSettings['enable_processing_unique_visitors_year_and_range'] == 1;
346 }
347
348 return $result;
349 }
350
351 /**
352 * If Piwik uses per-domain config file, make sure CustomLogo is unique
353 * @param $path
354 * @return mixed
355 */
356 public static function rewriteMiscUserPathWithInstanceId($path)
357 {
358 $tmp = StaticContainer::get('path.misc.user');
359 $path = self::rewritePathAppendPiwikInstanceId($path, $tmp);
360 return $path;
361 }
362
363 /**
364 * Returns true if the Piwik server appears to be working.
365 *
366 * If the Piwik server is in an error state (eg. some directories are not writable and Piwik displays error message),
367 * or if the Piwik server is "offline",
368 * this will return false..
369 *
370 * @param $piwikServerUrl
371 * @param bool $acceptInvalidSSLCertificates
372 * @throws Exception
373 * @return bool
374 */
375 public static function checkPiwikServerWorking($piwikServerUrl, $acceptInvalidSSLCertificates = false)
376 {
377 // Now testing if the webserver is running
378 try {
379 $fetched = Http::sendHttpRequestBy('curl',
380 $piwikServerUrl,
381 $timeout = 45,
382 $userAgent = null,
383 $destinationPath = null,
384 $file = null,
385 $followDepth = 0,
386 $acceptLanguage = false,
387 $acceptInvalidSSLCertificates
388 );
389 } catch (Exception $e) {
390 $fetched = "ERROR fetching: " . $e->getMessage();
391 }
392 // this will match when Piwik not installed yet, or favicon not customised
393 $expectedStringAlt = 'plugins/CoreHome/images/favicon.png';
394
395 // this will match when Piwik is installed and favicon has been customised
396 $expectedString = 'misc/user/';
397
398 // see checkPiwikIsNotInstalled()
399 $expectedStringAlreadyInstalled = 'piwik-is-already-installed';
400
401 $expectedStringNotFound = strpos($fetched, $expectedString) === false
402 && strpos($fetched, $expectedStringAlt) === false
403 && strpos($fetched, $expectedStringAlreadyInstalled) === false;
404
405 $hasError = false !== strpos($fetched, PAGE_TITLE_WHEN_ERROR);
406
407 if ($hasError || $expectedStringNotFound) {
408 throw new Exception("\nMatomo should be running at: "
409 . $piwikServerUrl
410 . " but this URL returned an unexpected response: '"
411 . $fetched . "'\n\n");
412 }
413 }
414
415 /**
416 * Returns true if Piwik is deployed using git
417 * FAQ: http://piwik.org/faq/how-to-install/faq_18271/
418 *
419 * @return bool
420 */
421 public static function isGitDeployment()
422 {
423 return file_exists(PIWIK_INCLUDE_PATH . '/.git/HEAD');
424 }
425
426 public static function getCurrentGitBranch()
427 {
428 $file = PIWIK_INCLUDE_PATH . '/.git/HEAD';
429 if (!file_exists($file)) {
430 return '';
431 }
432 $firstLineOfGitHead = file($file);
433 if (empty($firstLineOfGitHead)) {
434 return '';
435 }
436 $firstLineOfGitHead = $firstLineOfGitHead[0];
437 $parts = explode('/', $firstLineOfGitHead);
438 if (empty($parts[2])) {
439 return '';
440 }
441 $currentGitBranch = trim($parts[2]);
442 return $currentGitBranch;
443 }
444
445 /**
446 * @param $pathToRewrite
447 * @param $leadingPathToAppendHostnameTo
448 * @param $hostname
449 * @return mixed
450 * @throws \Exception
451 */
452 protected static function rewritePathAppendPiwikInstanceId($pathToRewrite, $leadingPathToAppendHostnameTo)
453 {
454 $instanceId = self::getPiwikInstanceId();
455 if (empty($instanceId)) {
456 return $pathToRewrite;
457 }
458
459 if (($posTmp = strrpos($pathToRewrite, $leadingPathToAppendHostnameTo)) === false) {
460 throw new Exception("The path $pathToRewrite was expected to contain the string $leadingPathToAppendHostnameTo");
461 }
462
463 $tmpToReplace = $leadingPathToAppendHostnameTo . $instanceId . '/';
464
465 // replace only the latest occurrence (in case path contains twice /tmp)
466 $pathToRewrite = substr_replace($pathToRewrite, $tmpToReplace, $posTmp, strlen($leadingPathToAppendHostnameTo));
467 return $pathToRewrite;
468 }
469
470 /**
471 * @throws \Exception
472 * @return string or False if not set
473 */
474 public static function getPiwikInstanceId()
475 {
476 // until Piwik is installed, we use hostname as instance_id
477 if (!self::isPiwikInstalled()
478 && Common::isPhpCliMode()) {
479 // enterprise:install use case
480 return Config::getHostname();
481 }
482
483 // config.ini.php not ready yet, instance_id will not be set
484 if (!Config::getInstance()->existsLocalConfig()) {
485 return false;
486 }
487
488 $instanceId = @Config::getInstance()->General['instance_id'];
489 if (!empty($instanceId)) {
490 return $instanceId;
491 }
492
493 // do not rewrite the path as Piwik uses the standard config.ini.php file
494 return false;
495 }
496
497 /**
498 * @param $currentUrl
499 */
500 public static function overwritePiwikUrl($currentUrl)
501 {
502 Option::set(self::OPTION_PIWIK_URL, $currentUrl, $autoLoad = true);
503 }
504
505 /**
506 * @return bool
507 */
508 public static function isHttpsForced()
509 {
510 if (!SettingsPiwik::isPiwikInstalled()) {
511 // Only enable this feature after Piwik is already installed
512 return false;
513 }
514 return Config::getInstance()->General['force_ssl'] == 1;
515 }
516
517 /**
518 * Note: this config settig is also checked in the InterSites plugin
519 *
520 * @return bool
521 */
522 public static function isSameFingerprintAcrossWebsites()
523 {
524 return (bool)Config::getInstance()->Tracker['enable_fingerprinting_across_websites'];
525 }
526 }
527