update Piwik to version 2.16 (fixes #91)

This commit is contained in:
oliver 2016-04-10 18:55:57 +02:00
commit d885a4baa9
5833 changed files with 418860 additions and 226988 deletions

View file

@ -0,0 +1,82 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Commands;
use Piwik\Container\StaticContainer;
use Piwik\Piwik;
use Piwik\Plugin\ConsoleCommand;
use Symfony\Component\Console\Input\InputArgument;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Console\Helper\Table;
/**
* Diagnostic command that analyzes a single archive table. Displays information like # of segment archives,
* # invalidated archives, # temporary archives, etc.
*/
class AnalyzeArchiveTable extends ConsoleCommand
{
protected function configure()
{
$this->setName('diagnostics:analyze-archive-table');
$this->setDescription('Analyze an archive table and display human readable information about what is stored. '
. 'This command can be used to diagnose issues like bloated archive tables.');
$this->addArgument('table-date', InputArgument::REQUIRED, "The table's associated date, eg, 2015_01 or 2015_02");
}
protected function execute(InputInterface $input, OutputInterface $output)
{
$tableDate = $input->getArgument('table-date');
$output->writeln("<comment>Statistics for the archive_numeric_$tableDate and archive_blob_$tableDate tables:</comment>");
$output->writeln("");
$archiveTableDao = StaticContainer::get('Piwik\DataAccess\ArchiveTableDao');
$rows = $archiveTableDao->getArchiveTableAnalysis($tableDate);
// process labels
$periodIdsToLabels = array_flip(Piwik::$idPeriods);
foreach ($rows as $key => &$row) {
list($idSite, $date1, $date2, $period) = explode('.', $key);
$periodLabel = isset($periodIdsToLabels[$period]) ? $periodIdsToLabels[$period] : "Unknown Period ($period)";
$row['label'] = $periodLabel . "[" . $date1 . " - " . $date2 . "] idSite = " . $idSite;
}
$headers = array('Group', '# Archives', '# Invalidated', '# Temporary', '# Error', '# Segment',
'# Numeric Rows', '# Blob Rows');
// display all rows
$table = new Table($output);
$table->setHeaders($headers)->setRows($rows);
$table->render();
// display summary
$totalArchives = 0;
$totalInvalidated = 0;
$totalTemporary = 0;
$totalError = 0;
$totalSegment = 0;
foreach ($rows as $row) {
$totalArchives += $row['count_archives'];
$totalInvalidated += $row['count_invalidated_archives'];
$totalTemporary += $row['count_temporary_archives'];
$totalError += $row['count_error_archives'];
$totalSegment += $row['count_segment_archives'];
}
$output->writeln("");
$output->writeln("Total # Archives: <comment>$totalArchives</comment>");
$output->writeln("Total # Invalidated Archives: <comment>$totalInvalidated</comment>");
$output->writeln("Total # Temporary Archives: <comment>$totalTemporary</comment>");
$output->writeln("Total # Error Archives: <comment>$totalError</comment>");
$output->writeln("Total # Segment Archives: <comment>$totalSegment</comment>");
$output->writeln("");
}
}

View file

@ -0,0 +1,89 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Commands;
use Piwik\Container\StaticContainer;
use Piwik\Plugin\ConsoleCommand;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResult;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResultItem;
use Piwik\Plugins\Diagnostics\DiagnosticService;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Input\InputOption;
use Symfony\Component\Console\Output\OutputInterface;
/**
* Run the diagnostics.
*/
class Run extends ConsoleCommand
{
protected function configure()
{
$this->setName('diagnostics:run')
->setDescription('Run diagnostics to check that Piwik is installed and runs correctly')
->addOption('all', null, InputOption::VALUE_NONE, 'Show all diagnostics, including those that passed with success');
}
protected function execute(InputInterface $input, OutputInterface $output)
{
// Replace this with dependency injection once available
/** @var DiagnosticService $diagnosticService */
$diagnosticService = StaticContainer::get('Piwik\Plugins\Diagnostics\DiagnosticService');
$showAll = $input->getOption('all');
$report = $diagnosticService->runDiagnostics();
foreach ($report->getAllResults() as $result) {
$items = $result->getItems();
if (! $showAll && ($result->getStatus() === DiagnosticResult::STATUS_OK)) {
continue;
}
if (count($items) === 1) {
$output->writeln($result->getLabel() . ': ' . $this->formatItem($items[0]), OutputInterface::OUTPUT_PLAIN);
continue;
}
$output->writeln($result->getLabel() . ':');
foreach ($items as $item) {
$output->writeln("\t- " . $this->formatItem($item), OutputInterface::OUTPUT_PLAIN);
}
}
if ($report->hasWarnings()) {
$output->writeln(sprintf('<comment>%d warnings detected</comment>', $report->getWarningCount()));
}
if ($report->hasErrors()) {
$output->writeln(sprintf('<error>%d errors detected</error>', $report->getErrorCount()));
return 1;
}
return 0;
}
private function formatItem(DiagnosticResultItem $item)
{
if ($item->getStatus() === DiagnosticResult::STATUS_ERROR) {
$tag = 'error';
} elseif ($item->getStatus() === DiagnosticResult::STATUS_WARNING) {
$tag = 'comment';
} else {
$tag = 'info';
}
return sprintf(
'<%s>%s %s</%s>',
$tag,
strtoupper($item->getStatus()),
preg_replace('/\<br\s*\/?\>/i', "\n", $item->getComment()),
$tag
);
}
}

View file

@ -0,0 +1,193 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics;
use Piwik\Development;
use Piwik\Ini\IniReader;
use Piwik\Application\Kernel\GlobalSettingsProvider;
use Piwik\Settings as PiwikSettings;
use Piwik\Plugin\Settings as PluginSettings;
/**
* A diagnostic report contains all the results of all the diagnostics.
*/
class ConfigReader
{
/**
* @var GlobalSettingsProvider
*/
private $settings;
/**
* @var IniReader
*/
private $iniReader;
public function __construct(GlobalSettingsProvider $settings, IniReader $iniReader)
{
$this->settings = $settings;
$this->iniReader = $iniReader;
}
public function getConfigValuesFromFiles()
{
$ini = $this->settings->getIniFileChain();
$descriptions = $this->iniReader->readComments($this->settings->getPathGlobal());
$copy = array();
foreach ($ini->getAll() as $category => $values) {
if ($this->shouldSkipCategory($category)) {
continue;
}
$local = $this->getFromLocalConfig($category);
if (empty($local)) {
$local = array();
}
$global = $this->getFromGlobalConfig($category);
if (empty($global)) {
$global = array();
}
$copy[$category] = array();
foreach ($values as $key => $value) {
$newValue = $value;
if ($this->isKeyAPassword($key)) {
$newValue = $this->getMaskedPassword();
}
$defaultValue = null;
if (array_key_exists($key, $global)) {
$defaultValue = $global[$key];
}
$description = '';
if (!empty($descriptions[$category][$key])) {
$description = trim($descriptions[$category][$key]);
}
$copy[$category][$key] = array(
'value' => $newValue,
'description' => $description,
'isCustomValue' => array_key_exists($key, $local),
'defaultValue' => $defaultValue,
);
}
}
return $copy;
}
private function shouldSkipCategory($category)
{
$category = strtolower($category);
if ($category === 'database') {
return true;
}
$developmentOnlySections = array('database_tests', 'tests', 'debugtests');
return !Development::isEnabled() && in_array($category, $developmentOnlySections);
}
public function getFromGlobalConfig($name)
{
return $this->settings->getIniFileChain()->getFrom($this->settings->getPathGlobal(), $name);
}
public function getFromLocalConfig($name)
{
return $this->settings->getIniFileChain()->getFrom($this->settings->getPathLocal(), $name);
}
private function getMaskedPassword()
{
return '******';
}
private function isKeyAPassword($key)
{
$key = strtolower($key);
$passwordFields = array(
'password', 'secret', 'apikey', 'privatekey', 'admin_pass'
);
foreach ($passwordFields as $value) {
if (strpos($key, $value) !== false) {
return true;
}
}
if ($key === 'salt') {
return true;
}
return false;
}
/**
* Adds config values that can be used to overwrite a plugin system setting and adds a description + default value
* for already existing configured config values that overwrite a plugin system setting.
*
* @param array $configValues
* @param \Piwik\Plugin\Settings[] $pluginSettings
* @return array
*/
public function addConfigValuesFromPluginSettings($configValues, $pluginSettings)
{
foreach ($pluginSettings as $pluginSetting) {
$pluginName = $pluginSetting->getPluginName();
if (empty($pluginName)) {
continue;
}
$configs[$pluginName] = array();
foreach ($pluginSetting->getSettings() as $setting) {
if ($setting instanceof PiwikSettings\SystemSetting && $setting->isReadableByCurrentUser()) {
$name = $setting->getName();
$description = '';
if (!empty($setting->description)) {
$description .= $setting->description . ' ';
}
if (!empty($setting->inlineHelp)) {
$description .= $setting->inlineHelp;
}
if (isset($configValues[$pluginName][$name])) {
$configValues[$pluginName][$name]['defaultValue'] = $setting->defaultValue;
$configValues[$pluginName][$name]['description'] = trim($description);
if ($setting->uiControlType === PluginSettings::CONTROL_PASSWORD) {
$value = $configValues[$pluginName][$name]['value'];
$configValues[$pluginName][$name]['value'] = $this->getMaskedPassword();
}
} else {
$defaultValue = $setting->getValue();
$configValues[$pluginName][$name] = array(
'value' => null,
'description' => trim($description),
'isCustomValue' => false,
'defaultValue' => $defaultValue
);
}
}
}
if (empty($configValues[$pluginName])) {
unset($configValues[$pluginName]);
}
}
return $configValues;
}
}

View file

@ -0,0 +1,66 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics;
use Piwik\Config;
use Piwik\Piwik;
use Piwik\View;
use Piwik\Settings;
class Controller extends \Piwik\Plugin\ControllerAdmin
{
/**
* @var ConfigReader
*/
private $configReader;
public function __construct(ConfigReader $configReader)
{
$this->configReader = $configReader;
parent::__construct();
}
public function configfile()
{
Piwik::checkUserHasSuperUserAccess();
$allSettings = Settings\Manager::getAllPluginSettings();
$configValues = $this->configReader->getConfigValuesFromFiles();
$configValues = $this->configReader->addConfigValuesFromPluginSettings($configValues, $allSettings);
$configValues = $this->sortConfigValues($configValues);
return $this->renderTemplate('configfile', array(
'allConfigValues' => $configValues
));
}
private function sortConfigValues($configValues)
{
// we sort by sections alphabetically
uksort($configValues, function ($section1, $section2) {
return strcasecmp($section1, $section2);
});
foreach ($configValues as $category => &$settings) {
// we sort keys alphabetically but list the ones that are changed first
uksort($settings, function ($setting1, $setting2) use ($settings) {
if ($settings[$setting1]['isCustomValue'] && !$settings[$setting2]['isCustomValue']) {
return -1;
} elseif (!$settings[$setting1]['isCustomValue'] && $settings[$setting2]['isCustomValue']) {
return 1;
}
return strcasecmp($setting1, $setting2);
});
}
return $configValues;
}
}

View file

@ -0,0 +1,48 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\CliMulti;
use Piwik\Config;
use Piwik\Http;
use Piwik\Translation\Translator;
use Piwik\Url;
/**
* Check if cron archiving can run through CLI.
*/
class CronArchivingCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckCronArchiveProcess');
$comment = $this->translator->translate('Installation_SystemCheckCronArchiveProcessCLI') . ': ';
$process = new CliMulti();
if ($process->supportsAsync()) {
$comment .= $this->translator->translate('General_Ok');
} else {
$comment .= $this->translator->translate('Installation_NotSupported')
. ' ' . $this->translator->translate('Goals_Optional');
}
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_OK, $comment));
}
}

View file

@ -0,0 +1,106 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Db\Adapter;
use Piwik\SettingsServer;
use Piwik\Translation\Translator;
/**
* Check supported DB adapters are available.
*/
class DbAdapterCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$results = array();
$results[] = $this->checkPdo();
$results = array_merge($results, $this->checkDbAdapters());
return $results;
}
private function checkPdo()
{
$label = 'PDO ' . $this->translator->translate('Installation_Extension');
if (extension_loaded('PDO')) {
$status = DiagnosticResult::STATUS_OK;
} else {
$status = DiagnosticResult::STATUS_WARNING;
}
return DiagnosticResult::singleResult($label, $status);
}
private function checkDbAdapters()
{
$results = array();
$adapters = Adapter::getAdapters();
foreach ($adapters as $adapter => $port) {
$label = $adapter . ' ' . $this->translator->translate('Installation_Extension');
$results[] = DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_OK);
}
if (empty($adapters)) {
$label = $this->translator->translate('Installation_SystemCheckDatabaseExtensions');
$comment = $this->translator->translate('Installation_SystemCheckDatabaseHelp');
$result = DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_ERROR, $comment);
$result->setLongErrorMessage($this->getLongErrorMessage());
$results[] = $result;
}
return $results;
}
private function getLongErrorMessage()
{
$message = '<p>';
if (SettingsServer::isWindows()) {
$message .= $this->translator->translate(
'Installation_SystemCheckWinPdoAndMysqliHelp',
array('<br /><br /><code>extension=php_mysqli.dll</code><br /><code>extension=php_pdo.dll</code><br /><code>extension=php_pdo_mysql.dll</code><br />')
);
} else {
$message .= $this->translator->translate(
'Installation_SystemCheckPdoAndMysqliHelp',
array(
'<br /><br /><code>--with-mysqli</code><br /><code>--with-pdo-mysql</code><br /><br />',
'<br /><br /><code>extension=mysqli.so</code><br /><code>extension=pdo.so</code><br /><code>extension=pdo_mysql.so</code><br />'
)
);
}
$message .= $this->translator->translate('Installation_RestartWebServer') . '<br/><br/>';
$message .= $this->translator->translate('Installation_SystemCheckPhpPdoAndMysqli', array(
'<a style="color:red" href="http://php.net/pdo">',
'</a>',
'<a style="color:red" href="http://php.net/mysqli">',
'</a>',
));
$message .= '</p>';
return $message;
}
}

View file

@ -0,0 +1,44 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
/**
* Performs a diagnostic on the system or Piwik.
*
* Example:
*
* class MyDiagnostic implements Diagnostic
* {
* public function execute()
* {
* $results = array();
*
* // First check (error)
* $status = testSomethingIsOk() ? DiagnosticResult::STATUS_OK : DiagnosticResult::STATUS_ERROR;
* $results[] = DiagnosticResult::singleResult('First check', $status);
*
* // Second check (warning)
* $status = testSomethingElseIsOk() ? DiagnosticResult::STATUS_OK : DiagnosticResult::STATUS_WARNING;
* $results[] = DiagnosticResult::singleResult('Second check', $status);
*
* return $results;
* }
* }
*
* Diagnostics are loaded with dependency injection support.
*
* @api
*/
interface Diagnostic
{
/**
* @return DiagnosticResult[]
*/
public function execute();
}

View file

@ -0,0 +1,121 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
/**
* The result of a diagnostic.
*
* @api
*/
class DiagnosticResult
{
const STATUS_ERROR = 'error';
const STATUS_WARNING = 'warning';
const STATUS_OK = 'ok';
/**
* @var string
*/
private $label;
/**
* @var string
*/
private $longErrorMessage = '';
/**
* @var DiagnosticResultItem[]
*/
private $items = array();
public function __construct($label)
{
$this->label = $label;
}
/**
* @param string $label
* @param string $status
* @param string $comment
* @return DiagnosticResult
*/
public static function singleResult($label, $status, $comment = '')
{
$result = new self($label);
$result->addItem(new DiagnosticResultItem($status, $comment));
return $result;
}
/**
* @return string
*/
public function getLabel()
{
return $this->label;
}
/**
* @return DiagnosticResultItem[]
*/
public function getItems()
{
return $this->items;
}
public function addItem(DiagnosticResultItem $item)
{
$this->items[] = $item;
}
/**
* @param DiagnosticResultItem[] $items
*/
public function setItems(array $items)
{
$this->items = $items;
}
/**
* @return string
*/
public function getLongErrorMessage()
{
return $this->longErrorMessage;
}
/**
* @param string $longErrorMessage
*/
public function setLongErrorMessage($longErrorMessage)
{
$this->longErrorMessage = $longErrorMessage;
}
/**
* Returns the worst status of the items.
*
* @return string One of the `STATUS_*` constants.
*/
public function getStatus()
{
$status = self::STATUS_OK;
foreach ($this->getItems() as $item) {
if ($item->getStatus() === self::STATUS_ERROR) {
return self::STATUS_ERROR;
}
if ($item->getStatus() === self::STATUS_WARNING) {
$status = self::STATUS_WARNING;
}
}
return $status;
}
}

View file

@ -0,0 +1,49 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
/**
* @api
*/
class DiagnosticResultItem
{
/**
* @var string
*/
private $status;
/**
* Optional comment about the item.
*
* @var string
*/
private $comment;
public function __construct($status, $comment = '')
{
$this->status = $status;
$this->comment = $comment;
}
/**
* @return string
*/
public function getStatus()
{
return $this->status;
}
/**
* @return string
*/
public function getComment()
{
return $this->comment;
}
}

View file

@ -0,0 +1,56 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Filechecks;
use Piwik\Translation\Translator;
/**
* Check the files integrity.
*/
class FileIntegrityCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckFileIntegrity');
$messages = Filechecks::getFileIntegrityInformation();
$ok = array_shift($messages);
if (empty($messages)) {
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_OK));
}
if ($ok) {
$status = DiagnosticResult::STATUS_WARNING;
return array(DiagnosticResult::singleResult($label, $status, $messages[0]));
}
$comment = $this->translator->translate('General_FileIntegrityWarningExplanation');
// Keep only the 20 first lines else it becomes unmanageable
if (count($messages) > 20) {
$messages = array_slice($messages, 0, 20);
$messages[] = '...';
}
$comment .= '<br/><br/><pre style="overflow-x: scroll;max-width: 600px;">'
. implode("\n", $messages) . '</pre>';
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_WARNING, $comment));
}
}

View file

@ -0,0 +1,45 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Config;
use Piwik\SettingsServer;
use Piwik\Translation\Translator;
/**
* Check that the GD extension is installed and the correct version.
*/
class GdExtensionCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckGDFreeType');
if (SettingsServer::isGdExtensionEnabled()) {
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_OK));
}
$comment = sprintf(
'%s<br />%s',
$this->translator->translate('Installation_SystemCheckGDFreeType'),
$this->translator->translate('Installation_SystemCheckGDHelp')
);
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_WARNING, $comment));
}
}

View file

@ -0,0 +1,50 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Config;
use Piwik\Filechecks;
use Piwik\Http;
use Piwik\Translation\Translator;
/**
* Check that Piwik's HTTP client can work correctly.
*/
class HttpClientCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckOpenURL');
$httpMethod = Http::getTransportMethod();
if ($httpMethod) {
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_OK, $httpMethod));
}
$canAutoUpdate = Filechecks::canAutoUpdate();
$comment = $this->translator->translate('Installation_SystemCheckOpenURLHelp');
if (! $canAutoUpdate) {
$comment .= '<br/>' . $this->translator->translate('Installation_SystemCheckAutoUpdateHelp');
}
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_WARNING, $comment));
}
}

View file

@ -0,0 +1,87 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Common;
use Piwik\Config;
use Piwik\Db;
use Piwik\Translation\Translator;
/**
* Check if Piwik can use LOAD DATA INFILE.
*/
class LoadDataInfileCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$isPiwikInstalling = !Config::getInstance()->existsLocalConfig();
if ($isPiwikInstalling) {
// Skip the diagnostic if Piwik is being installed
return array();
}
$label = $this->translator->translate('Installation_DatabaseAbilities');
$optionTable = Common::prefixTable('option');
$testOptionNames = array('test_system_check1', 'test_system_check2');
$loadDataInfile = false;
$errorMessage = null;
try {
$loadDataInfile = Db\BatchInsert::tableInsertBatch(
$optionTable,
array('option_name', 'option_value'),
array(
array($testOptionNames[0], '1'),
array($testOptionNames[1], '2'),
),
$throwException = true,
$charset = 'latin1'
);
} catch (\Exception $ex) {
$errorMessage = str_replace("\n", "<br/>", $ex->getMessage());
}
// delete the temporary rows that were created
Db::exec("DELETE FROM `$optionTable` WHERE option_name IN ('" . implode("','", $testOptionNames) . "')");
if ($loadDataInfile) {
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_OK, 'LOAD DATA INFILE'));
}
$comment = sprintf(
'LOAD DATA INFILE<br/>%s<br/>%s',
$this->translator->translate('Installation_LoadDataInfileUnavailableHelp', array(
'LOAD DATA INFILE',
'FILE',
)),
$this->translator->translate('Installation_LoadDataInfileRecommended')
);
if ($errorMessage) {
$comment .= sprintf(
'<br/><strong>%s:</strong> %s<br/>%s',
$this->translator->translate('General_Error'),
$errorMessage,
'Troubleshooting: <a target="_blank" href="?module=Proxy&action=redirect&url=http://piwik.org/faq/troubleshooting/%23faq_194">FAQ on piwik.org</a>'
);
}
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_WARNING, $comment));
}
}

View file

@ -0,0 +1,57 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Config;
use Piwik\SettingsServer;
use Piwik\Translation\Translator;
/**
* Check that the memory limit is enough.
*/
class MemoryLimitCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
/**
* @var int
*/
private $minimumMemoryLimit;
public function __construct(Translator $translator, $minimumMemoryLimit)
{
$this->translator = $translator;
$this->minimumMemoryLimit = $minimumMemoryLimit;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckMemoryLimit');
SettingsServer::raiseMemoryLimitIfNecessary();
$memoryLimit = SettingsServer::getMemoryLimitValue();
$comment = $memoryLimit . 'M';
if ($memoryLimit >= $this->minimumMemoryLimit) {
$status = DiagnosticResult::STATUS_OK;
} else {
$status = DiagnosticResult::STATUS_WARNING;
$comment .= sprintf(
'<br />%s<br />%s',
$this->translator->translate('Installation_SystemCheckMemoryLimitHelp'),
$this->translator->translate('Installation_RestartWebServer')
);
}
return array(DiagnosticResult::singleResult($label, $status, $comment));
}
}

View file

@ -0,0 +1,55 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Config;
use Piwik\Filesystem;
use Piwik\Translation\Translator;
/**
* Checks if the filesystem Piwik stores sessions in is NFS or not.
*
* This check is done in order to avoid using file based sessions on NFS system,
* since on such a filesystem file locking can make file based sessions incredibly slow.
*/
class NfsDiskCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_Filesystem');
if (! Filesystem::checkIfFileSystemIsNFS()) {
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_OK));
}
$isPiwikInstalling = !Config::getInstance()->existsLocalConfig();
if ($isPiwikInstalling) {
$help = 'Installation_NfsFilesystemWarningSuffixInstall';
} else {
$help = 'Installation_NfsFilesystemWarningSuffixAdmin';
}
$comment = sprintf(
'%s<br />%s',
$this->translator->translate('Installation_NfsFilesystemWarning'),
$this->translator->translate($help)
);
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_WARNING, $comment));
}
}

View file

@ -0,0 +1,80 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Config;
use Piwik\Http;
use Piwik\Translation\Translator;
use Piwik\Url;
use Psr\Log\LoggerInterface;
/**
* Check that mod_pagespeed is not enabled.
*/
class PageSpeedCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
/**
* @var LoggerInterface
*/
private $logger;
public function __construct(Translator $translator, LoggerInterface $logger)
{
$this->translator = $translator;
$this->logger = $logger;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckPageSpeedDisabled');
if (! $this->isPageSpeedEnabled()) {
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_OK));
}
$comment = $this->translator->translate('Installation_SystemCheckPageSpeedWarn', array(
'(eg. Apache, Nginx or IIS)',
));
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_WARNING, $comment));
}
private function isPageSpeedEnabled()
{
$url = Url::getCurrentUrlWithoutQueryString() . '?module=Installation&action=getEmptyPageForSystemCheck';
try {
$page = Http::sendHttpRequest($url,
$timeout = 1,
$userAgent = null,
$destinationPath = null,
$followDepth = 0,
$acceptLanguage = false,
$byteRange = false,
// Return headers
$getExtendedInfo = true
);
} catch(\Exception $e) {
$this->logger->info('Unable to test if mod_pagespeed is enabled: the request to {url} failed', array(
'url' => $url,
));
// If the test failed, we assume Page speed is not enabled
return false;
}
$headers = $page['headers'];
return isset($headers['X-Mod-Pagespeed']) || isset($headers['X-Page-Speed']);
}
}

View file

@ -0,0 +1,85 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Translation\Translator;
/**
* Check the PHP extensions.
*/
class PhpExtensionsCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckExtensions');
$result = new DiagnosticResult($label);
$longErrorMessage = '';
$requiredExtensions = $this->getRequiredExtensions();
foreach ($requiredExtensions as $extension) {
if (! extension_loaded($extension)) {
$status = DiagnosticResult::STATUS_ERROR;
$comment = $extension . ': ' . $this->translator->translate('Installation_RestartWebServer');
$longErrorMessage .= '<p>' . $this->getHelpMessage($extension) . '</p>';
} else {
$status = DiagnosticResult::STATUS_OK;
$comment = $extension;
}
$result->addItem(new DiagnosticResultItem($status, $comment));
}
$result->setLongErrorMessage($longErrorMessage);
return array($result);
}
/**
* @return string[]
*/
private function getRequiredExtensions()
{
$requiredExtensions = array(
'zlib',
'SPL',
'iconv',
'json',
'mbstring',
'Reflection',
);
return $requiredExtensions;
}
private function getHelpMessage($missingExtension)
{
$messages = array(
'zlib' => 'Installation_SystemCheckZlibHelp',
'SPL' => 'Installation_SystemCheckSplHelp',
'iconv' => 'Installation_SystemCheckIconvHelp',
'json' => 'Installation_SystemCheckWarnJsonHelp',
'mbstring' => 'Installation_SystemCheckMbstringHelp',
'Reflection' => 'Required extension that is built in PHP, see http://www.php.net/manual/en/book.reflection.php',
);
return $this->translator->translate($messages[$missingExtension]);
}
}

View file

@ -0,0 +1,111 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Translation\Translator;
/**
* Check the enabled PHP functions.
*/
class PhpFunctionsCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckFunctions');
$result = new DiagnosticResult($label);
foreach ($this->getRequiredFunctions() as $function) {
if (! self::functionExists($function)) {
$status = DiagnosticResult::STATUS_ERROR;
$comment = sprintf(
'%s <br/><br/><em>%s</em><br/><em>%s</em><br/>',
$function,
$this->getHelpMessage($function),
$this->translator->translate('Installation_RestartWebServer')
);
} else {
$status = DiagnosticResult::STATUS_OK;
$comment = $function;
}
$result->addItem(new DiagnosticResultItem($status, $comment));
}
return array($result);
}
/**
* @return string[]
*/
private function getRequiredFunctions()
{
return array(
'debug_backtrace',
'create_function',
'eval',
'gzcompress',
'gzuncompress',
'pack',
);
}
/**
* Tests if a function exists. Also handles the case where a function is disabled via Suhosin.
*
* @param string $function
* @return bool
*/
public static function functionExists($function)
{
// eval() is a language construct
if ($function == 'eval') {
// does not check suhosin.executor.eval.whitelist (or blacklist)
if (extension_loaded('suhosin')) {
return @ini_get("suhosin.executor.disable_eval") != "1";
}
return true;
}
$exists = function_exists($function);
if (extension_loaded('suhosin')) {
$blacklist = @ini_get("suhosin.executor.func.blacklist");
if (!empty($blacklist)) {
$blacklistFunctions = array_map('strtolower', array_map('trim', explode(',', $blacklist)));
return $exists && !in_array($function, $blacklistFunctions);
}
}
return $exists;
}
private function getHelpMessage($missingFunction)
{
$messages = array(
'debug_backtrace' => 'Installation_SystemCheckDebugBacktraceHelp',
'create_function' => 'Installation_SystemCheckCreateFunctionHelp',
'eval' => 'Installation_SystemCheckEvalHelp',
'gzcompress' => 'Installation_SystemCheckGzcompressHelp',
'gzuncompress' => 'Installation_SystemCheckGzuncompressHelp',
'pack' => 'Installation_SystemCheckPackHelp',
);
return $this->translator->translate($messages[$missingFunction]);
}
}

View file

@ -0,0 +1,86 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Translation\Translator;
/**
* Check some PHP INI settings.
*/
class PhpSettingsCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckSettings');
$result = new DiagnosticResult($label);
foreach ($this->getRequiredSettings() as $setting) {
list($settingName, $requiredValue) = explode('=', $setting);
$currentValue = (int) ini_get($settingName);
if ($currentValue != $requiredValue) {
$status = DiagnosticResult::STATUS_ERROR;
$comment = sprintf(
'%s <br/><br/><em>%s</em><br/><em>%s</em><br/>',
$setting,
$this->translator->translate('Installation_SystemCheckPhpSetting', array($setting)),
$this->translator->translate('Installation_RestartWebServer')
);
} else {
$status = DiagnosticResult::STATUS_OK;
$comment = $setting;
}
$result->addItem(new DiagnosticResultItem($status, $comment));
}
return array($result);
}
/**
* @return string[]
*/
private function getRequiredSettings()
{
$requiredSettings = array(
// setting = required value
// Note: value must be an integer only
'session.auto_start=0',
);
if ($this->isPhpVersionAtLeast56() && ! defined("HHVM_VERSION") && !$this->isPhpVersionAtLeast70()) {
// always_populate_raw_post_data must be -1
// removed in PHP 7
$requiredSettings[] = 'always_populate_raw_post_data=-1';
}
return $requiredSettings;
}
private function isPhpVersionAtLeast56()
{
return version_compare(PHP_VERSION, '5.6', '>=');
}
private function isPhpVersionAtLeast70()
{
return version_compare(PHP_VERSION, '7.0.0-dev', '>=');
}
}

View file

@ -0,0 +1,58 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Translation\Translator;
/**
* Check the PHP version.
*/
class PhpVersionCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
global $piwik_minimumPHPVersion;
$actualVersion = PHP_VERSION;
$label = sprintf(
'%s >= %s',
$this->translator->translate('Installation_SystemCheckPhp'),
$piwik_minimumPHPVersion
);
if ($this->isPhpVersionValid($piwik_minimumPHPVersion, $actualVersion)) {
$status = DiagnosticResult::STATUS_OK;
$comment = $actualVersion;
} else {
$status = DiagnosticResult::STATUS_ERROR;
$comment = sprintf(
'%s: %s',
$this->translator->translate('General_Error'),
$this->translator->translate('General_Required', array($label))
);
}
return array(DiagnosticResult::singleResult($label, $status, $comment));
}
private function isPhpVersionValid($requiredVersion, $actualVersion)
{
return version_compare($requiredVersion, $actualVersion) <= 0;
}
}

View file

@ -0,0 +1,77 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Translation\Translator;
/**
* Check the PHP extensions that are not required but recommended.
*/
class RecommendedExtensionsCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckOtherExtensions');
$result = new DiagnosticResult($label);
$loadedExtensions = @get_loaded_extensions();
$loadedExtensions = array_map(function ($extension) {
return strtolower($extension);
}, $loadedExtensions);
foreach ($this->getRecommendedExtensions() as $extension) {
if (! in_array(strtolower($extension), $loadedExtensions)) {
$status = DiagnosticResult::STATUS_WARNING;
$comment = $extension . '<br/>' . $this->getHelpMessage($extension);
} else {
$status = DiagnosticResult::STATUS_OK;
$comment = $extension;
}
$result->addItem(new DiagnosticResultItem($status, $comment));
}
return array($result);
}
/**
* @return string[]
*/
private function getRecommendedExtensions()
{
return array(
'json',
'libxml',
'dom',
'SimpleXML',
);
}
private function getHelpMessage($missingExtension)
{
$messages = array(
'json' => 'Installation_SystemCheckWarnJsonHelp',
'libxml' => 'Installation_SystemCheckWarnLibXmlHelp',
'dom' => 'Installation_SystemCheckWarnDomHelp',
'SimpleXML' => 'Installation_SystemCheckWarnSimpleXMLHelp',
);
return $this->translator->translate($messages[$missingExtension]);
}
}

View file

@ -0,0 +1,76 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Translation\Translator;
/**
* Check the PHP functions that are not required but recommended.
*/
class RecommendedFunctionsCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckOtherFunctions');
$result = new DiagnosticResult($label);
foreach ($this->getRecommendedFunctions() as $function) {
if (! PhpFunctionsCheck::functionExists($function)) {
$status = DiagnosticResult::STATUS_WARNING;
$comment = $function . '<br/>' . $this->getHelpMessage($function);
} else {
$status = DiagnosticResult::STATUS_OK;
$comment = $function;
}
$result->addItem(new DiagnosticResultItem($status, $comment));
}
return array($result);
}
/**
* @return string[]
*/
private function getRecommendedFunctions()
{
return array(
'shell_exec',
'set_time_limit',
'mail',
'parse_ini_file',
'glob',
'gzopen',
);
}
private function getHelpMessage($function)
{
$messages = array(
'shell_exec' => 'Installation_SystemCheckFunctionHelp',
'set_time_limit' => 'Installation_SystemCheckTimeLimitHelp',
'mail' => 'Installation_SystemCheckMailHelp',
'parse_ini_file' => 'Installation_SystemCheckParseIniFileHelp',
'glob' => 'Installation_SystemCheckGlobHelp',
'gzopen' => 'Installation_SystemCheckZlibHelp',
);
return $this->translator->translate($messages[$function]);
}
}

View file

@ -0,0 +1,45 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Config;
use Piwik\SettingsServer;
use Piwik\Translation\Translator;
/**
* Check that the PHP timezone setting is set.
*/
class TimezoneCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('SitesManager_Timezone');
if (SettingsServer::isTimezoneSupportEnabled()) {
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_OK));
}
$comment = sprintf(
'%s<br />%s.',
$this->translator->translate('SitesManager_AdvancedTimezoneSupportNotFound'),
'<a href="http://php.net/manual/en/datetime.installation.php" rel="noreferrer" target="_blank">Timezone PHP documentation</a>'
);
return array(DiagnosticResult::singleResult($label, DiagnosticResult::STATUS_WARNING, $comment));
}
}

View file

@ -0,0 +1,49 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\Common;
use Piwik\Translation\Translator;
/**
* Check that the tracker is working correctly.
*/
class TrackerCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
public function __construct(Translator $translator)
{
$this->translator = $translator;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckTracker');
$trackerStatus = Common::getRequestVar('trackerStatus', 0, 'int');
if ($trackerStatus == 0) {
$status = DiagnosticResult::STATUS_OK;
$comment = '';
} else {
$status = DiagnosticResult::STATUS_WARNING;
$comment = sprintf(
'%s<br />%s<br />%s',
$trackerStatus,
$this->translator->translate('Installation_SystemCheckTrackerHelp'),
$this->translator->translate('Installation_RestartWebServer')
);
}
return array(DiagnosticResult::singleResult($label, $status, $comment));
}
}

View file

@ -0,0 +1,99 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Diagnostic;
use Piwik\DbHelper;
use Piwik\Filechecks;
use Piwik\Translation\Translator;
/**
* Check the permissions for some directories.
*/
class WriteAccessCheck implements Diagnostic
{
/**
* @var Translator
*/
private $translator;
/**
* Path to the temp directory.
* @var string
*/
private $tmpPath;
/**
* @param Translator $translator
* @param string $tmpPath Path to the temp directory.
*/
public function __construct(Translator $translator, $tmpPath)
{
$this->translator = $translator;
$this->tmpPath = $tmpPath;
}
public function execute()
{
$label = $this->translator->translate('Installation_SystemCheckWriteDirs');
$result = new DiagnosticResult($label);
$directories = Filechecks::checkDirectoriesWritable($this->getDirectories());
$error = false;
foreach ($directories as $directory => $isWritable) {
if ($isWritable) {
$status = DiagnosticResult::STATUS_OK;
} else {
$status = DiagnosticResult::STATUS_ERROR;
$error = true;
}
$result->addItem(new DiagnosticResultItem($status, $directory));
}
if ($error) {
$longErrorMessage = $this->translator->translate('Installation_SystemCheckWriteDirsHelp');
$longErrorMessage .= '<ul>';
foreach ($directories as $directory => $isWritable) {
if (! $isWritable) {
$longErrorMessage .= sprintf('<li><pre>chmod a+w %s</pre></li>', $directory);
}
}
$longErrorMessage .= '</ul>';
$result->setLongErrorMessage($longErrorMessage);
}
return array($result);
}
/**
* @return string[]
*/
private function getDirectories()
{
$directoriesToCheck = array(
$this->tmpPath,
$this->tmpPath . '/assets/',
$this->tmpPath . '/cache/',
$this->tmpPath . '/climulti/',
$this->tmpPath . '/latest/',
$this->tmpPath . '/logs/',
$this->tmpPath . '/sessions/',
$this->tmpPath . '/tcpdf/',
$this->tmpPath . '/templates_c/',
);
if (! DbHelper::isInstalled()) {
// at install, need /config to be writable (so we can create config.ini.php)
$directoriesToCheck[] = '/config/';
}
return $directoriesToCheck;
}
}

View file

@ -0,0 +1,118 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResult;
/**
* A diagnostic report contains all the results of all the diagnostics.
*/
class DiagnosticReport
{
/**
* @var DiagnosticResult[]
*/
private $mandatoryDiagnosticResults;
/**
* @var DiagnosticResult[]
*/
private $optionalDiagnosticResults;
/**
* @var int
*/
private $errorCount = 0;
/**
* @var int
*/
private $warningCount = 0;
/**
* @param DiagnosticResult[] $mandatoryDiagnosticResults
* @param DiagnosticResult[] $optionalDiagnosticResults
*/
public function __construct(array $mandatoryDiagnosticResults, array $optionalDiagnosticResults)
{
$this->mandatoryDiagnosticResults = $mandatoryDiagnosticResults;
$this->optionalDiagnosticResults = $optionalDiagnosticResults;
$this->computeErrorAndWarningCount();
}
/**
* @return bool
*/
public function hasErrors()
{
return $this->getErrorCount() > 0;
}
/**
* @return bool
*/
public function hasWarnings()
{
return $this->getWarningCount() > 0;
}
/**
* @return int
*/
public function getErrorCount()
{
return $this->errorCount;
}
/**
* @return int
*/
public function getWarningCount()
{
return $this->warningCount;
}
/**
* @return DiagnosticResult[]
*/
public function getAllResults()
{
return array_merge($this->mandatoryDiagnosticResults, $this->optionalDiagnosticResults);
}
/**
* @return DiagnosticResult[]
*/
public function getMandatoryDiagnosticResults()
{
return $this->mandatoryDiagnosticResults;
}
/**
* @return DiagnosticResult[]
*/
public function getOptionalDiagnosticResults()
{
return $this->optionalDiagnosticResults;
}
private function computeErrorAndWarningCount()
{
foreach ($this->getAllResults() as $result) {
switch ($result->getStatus()) {
case DiagnosticResult::STATUS_ERROR:
$this->errorCount++;
break;
case DiagnosticResult::STATUS_WARNING:
$this->warningCount++;
break;
}
}
}
}

View file

@ -0,0 +1,73 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics;
use Piwik\Plugins\Diagnostics\Diagnostic\Diagnostic;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResult;
/**
* Runs the Piwik diagnostics.
*
* @api
*/
class DiagnosticService
{
/**
* @var Diagnostic[]
*/
private $mandatoryDiagnostics;
/**
* @var Diagnostic[]
*/
private $optionalDiagnostics;
/**
* @param Diagnostic[] $mandatoryDiagnostics
* @param Diagnostic[] $optionalDiagnostics
* @param Diagnostic[] $disabledDiagnostics
*/
public function __construct(array $mandatoryDiagnostics, array $optionalDiagnostics, array $disabledDiagnostics)
{
$this->mandatoryDiagnostics = $this->removeDisabledDiagnostics($mandatoryDiagnostics, $disabledDiagnostics);
$this->optionalDiagnostics = $this->removeDisabledDiagnostics($optionalDiagnostics, $disabledDiagnostics);
}
/**
* @return DiagnosticReport
*/
public function runDiagnostics()
{
return new DiagnosticReport(
$this->run($this->mandatoryDiagnostics),
$this->run($this->optionalDiagnostics)
);
}
/**
* @param Diagnostic[] $diagnostics
* @return DiagnosticResult[]
*/
private function run(array $diagnostics)
{
$results = array();
foreach ($diagnostics as $diagnostic) {
$results = array_merge($results, $diagnostic->execute());
}
return $results;
}
private function removeDisabledDiagnostics(array $diagnostics, array $disabledDiagnostics)
{
return array_filter($diagnostics, function (Diagnostic $diagnostic) use ($disabledDiagnostics) {
return ! in_array($diagnostic, $disabledDiagnostics, true);
});
}
}

View file

@ -0,0 +1,30 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics;
use Piwik\Plugin;
class Diagnostics extends Plugin
{
/**
* @see Piwik\Plugin::registerEvents
*/
public function registerEvents()
{
return array(
'AssetManager.getStylesheetFiles' => 'getStylesheetFiles',
);
}
public function getStylesheetFiles(&$stylesheets)
{
$stylesheets[] = "plugins/Diagnostics/stylesheets/configfile.less";
}
}

View file

@ -0,0 +1,28 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics;
use Piwik\Menu\MenuAdmin;
use Piwik\Piwik;
/**
* This class allows you to add, remove or rename menu items.
* To configure a menu (such as Admin Menu, Reporting Menu, User Menu...) simply call the corresponding methods as
* described in the API-Reference http://developer.piwik.org/api-reference/Piwik/Menu/MenuAbstract
*/
class Menu extends \Piwik\Plugin\Menu
{
public function configureAdminMenu(MenuAdmin $menu)
{
if (Piwik::hasUserSuperUserAccess()) {
$menu->addDiagnosticItem('Diagnostics_ConfigFileTitle', $this->urlForAction('configfile'), $orderId = 30);
}
}
}

View file

@ -0,0 +1,99 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Test\Integration\Commands;
use Piwik\Tests\Fixtures\OneVisitorTwoVisits;
use Piwik\Tests\Framework\TestCase\ConsoleCommandTestCase;
use Piwik\Plugins\VisitsSummary\API as VisitsSummaryAPI;
/**
* TODO: This could be a unit test if we could inject the ArchiveTableDao in the command
* @group AnalyzeArchiveTableTest
*/
class AnalyzeArchiveTableTest extends ConsoleCommandTestCase
{
/**
* @var OneVisitorTwoVisits
*/
public static $fixture = null;
public static function setUpBeforeClass()
{
parent::setUpBeforeClass();
// make sure archiving is initiated so there is data in the archive tables
VisitsSummaryAPI::getInstance()->get(self::$fixture->idSite, 'month', '2010-03-01');
VisitsSummaryAPI::getInstance()->get(self::$fixture->idSite, 'month', '2010-03-01', 'browserCode==FF');
VisitsSummaryAPI::getInstance()->get(self::$fixture->idSite, 'month', '2010-03-01', 'daysSinceFirstVisit==2');
}
public function test_CommandOutput_IsAsExpected()
{
$expected = <<<OUTPUT
Statistics for the archive_numeric_2010_03 and archive_blob_2010_03 tables:
+-------------------------------------------+------------+---------------+-------------+---------+-----------+----------------+-------------+
| Group | # Archives | # Invalidated | # Temporary | # Error | # Segment | # Numeric Rows | # Blob Rows |
+-------------------------------------------+------------+---------------+-------------+---------+-----------+----------------+-------------+
| week[2010-03-01 - 2010-03-07] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 36 | 63 |
| month[2010-03-01 - 2010-03-31] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 36 | 63 |
| day[2010-03-03 - 2010-03-03] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-04 - 2010-03-04] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-05 - 2010-03-05] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-06 - 2010-03-06] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 36 | 51 |
| day[2010-03-07 - 2010-03-07] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-08 - 2010-03-08] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| week[2010-03-08 - 2010-03-14] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-09 - 2010-03-09] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-10 - 2010-03-10] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-11 - 2010-03-11] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-12 - 2010-03-12] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-13 - 2010-03-13] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-14 - 2010-03-14] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-15 - 2010-03-15] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| week[2010-03-15 - 2010-03-21] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-16 - 2010-03-16] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-17 - 2010-03-17] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-18 - 2010-03-18] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-19 - 2010-03-19] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-20 - 2010-03-20] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-21 - 2010-03-21] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-22 - 2010-03-22] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| week[2010-03-22 - 2010-03-28] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-23 - 2010-03-23] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-24 - 2010-03-24] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-25 - 2010-03-25] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-26 - 2010-03-26] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-27 - 2010-03-27] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-28 - 2010-03-28] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-29 - 2010-03-29] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-30 - 2010-03-30] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
| day[2010-03-31 - 2010-03-31] idSite = 1 | 3 | 0 | 0 | 0 | 2 | 0 | 0 |
+-------------------------------------------+------------+---------------+-------------+---------+-----------+----------------+-------------+
Total # Archives: 102
Total # Invalidated Archives: 0
Total # Temporary Archives: 0
Total # Error Archives: 0
Total # Segment Archives: 68
OUTPUT;
$this->applicationTester->run(array(
'command' => 'diagnostics:analyze-archive-table',
'table-date' => '2010_03',
));
$actual = $this->applicationTester->getDisplay();
$this->assertEquals($expected, $actual);
}
}
AnalyzeArchiveTableTest::$fixture = new OneVisitorTwoVisits();

View file

@ -0,0 +1,261 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Test\Integration\Commands;
use Piwik\Application\Kernel\GlobalSettingsProvider;
use Piwik\Ini\IniReader;
use Piwik\Plugins\Diagnostics\ConfigReader;
use Piwik\Plugins\ExampleSettingsPlugin\Settings;
use Piwik\Tests\Fixtures\OneVisitorTwoVisits;
use Piwik\Tests\Framework\TestCase\IntegrationTestCase;
/**
* TODO: This could be a unit test if we could inject the ArchiveTableDao in the command
* @group Diagnostics
* @group Plugins
*/
class ConfigReaderTest extends IntegrationTestCase
{
/**
* @var ConfigReader
*/
private $configReader;
public function setUp()
{
$settings = new GlobalSettingsProvider($this->configPath('global.ini.php'), $this->configPath('config.ini.php'), $this->configPath('common.config.ini.php'));
$this->configReader = new ConfigReader($settings, new IniReader());
}
public function test_getConfigValuesFromFiles()
{
$fileConfig = $this->configReader->getConfigValuesFromFiles();
$expected = array (
'Category' =>
array (
'key1' =>
array (
'value' => 'value_overwritten',
'description' => '',
'isCustomValue' => true,
'defaultValue' => 'value1',
),
'key2' =>
array (
'value' => 'valueCommon',
'description' => '',
'isCustomValue' => false,
'defaultValue' => 'value2',
),
'key3' =>
array (
'value' => '${@piwik(crash))}',
'description' => '',
'isCustomValue' => false,
'defaultValue' => NULL,
),
),
'CategoryOnlyInGlobalFile' =>
array (
'key3' =>
array (
'value' => 'value3',
'description' => 'test comment',
'isCustomValue' => false,
'defaultValue' => 'value3',
),
'key4' =>
array (
'value' => 'value4',
'description' => 'test comment 4',
'isCustomValue' => false,
'defaultValue' => 'value4',
),
),
'TestArray' =>
array (
'installed' =>
array (
'value' =>
array (
0 => 'plugin"1',
1 => 'plugin2',
2 => 'plugin3',
),
'description' => 'test comment 2
with multiple lines',
'isCustomValue' => true,
'defaultValue' =>
array (
0 => 'plugin1',
1 => 'plugin4',
),
),
),
'TestArrayOnlyInGlobalFile' =>
array (
'my_array' =>
array (
'value' =>
array (
0 => 'value1',
1 => 'value2',
),
'description' => '',
'isCustomValue' => false,
'defaultValue' =>
array (
0 => 'value1',
1 => 'value2',
),
),
),
'GeneralSection' =>
array (
'password' =>
array (
'value' => '******',
'description' => '',
'isCustomValue' => true,
'defaultValue' => NULL,
),
'login' =>
array (
'value' => 'tes"t',
'description' => '',
'isCustomValue' => true,
'defaultValue' => NULL,
),
),
'TestOnlyInCommon' =>
array (
'value' =>
array (
'value' => 'commonValue',
'description' => '',
'isCustomValue' => false,
'defaultValue' => NULL,
),
),
'Tracker' =>
array (
'commonConfigTracker' =>
array (
'value' => 'commonConfigTrackerValue',
'description' => '',
'isCustomValue' => false,
'defaultValue' => NULL,
),
),
);
$this->assertEquals($expected, $fileConfig);
}
public function test_addConfigValuesFromPluginSettings()
{
$settings = new Settings();
$configValues = $this->configReader->addConfigValuesFromPluginSettings(array(), array($settings));
$expected = array (
'ExampleSettingsPlugin' =>
array (
'metric' =>
array (
'value' => NULL,
'description' => 'Choose the metric that should be displayed in the browser tab',
'isCustomValue' => false,
'defaultValue' => 'nb_visits',
),
'browsers' =>
array (
'value' => NULL,
'description' => 'The value will be only displayed in the following browsers',
'isCustomValue' => false,
'defaultValue' =>
array (
0 => 'firefox',
1 => 'chromium',
2 => 'safari',
),
),
'description' =>
array (
'value' => NULL,
'description' => 'This description will be displayed next to the value',
'isCustomValue' => false,
'defaultValue' => 'This is the value:
Another line',
),
'password' =>
array (
'value' => NULL,
'description' => 'Password for the 3rd API where we fetch the value',
'isCustomValue' => false,
'defaultValue' => NULL,
),
),
);
$this->assertEquals($expected, $configValues);
}
public function test_addConfigValuesFromPluginSettings_shouldAddDescriptionAndDefaultValueForExistingConfigValues()
{
$settings = new Settings();
$existing = array(
'ExampleSettingsPlugin' =>
array (
'metric' =>
array (
'value' => NULL,
'description' => '',
'isCustomValue' => false,
'defaultValue' => null,
),
)
);
$configValues = $this->configReader->addConfigValuesFromPluginSettings($existing, array($settings));
$this->assertSame('Choose the metric that should be displayed in the browser tab', $configValues['ExampleSettingsPlugin']['metric']['description']);
$this->assertSame('nb_visits', $configValues['ExampleSettingsPlugin']['metric']['defaultValue']);
}
public function test_addConfigValuesFromPluginSettings_shouldMaskValueIfTypeIsPassword()
{
$settings = new Settings();
$settings->metric->uiControlType = Settings::CONTROL_PASSWORD;
$existing = array(
'ExampleSettingsPlugin' =>
array (
'metric' =>
array (
'value' => 'test',
'description' => '',
'isCustomValue' => false,
'defaultValue' => null,
),
)
);
$configValues = $this->configReader->addConfigValuesFromPluginSettings($existing, array($settings));
$this->assertSame('******', $configValues['ExampleSettingsPlugin']['metric']['value']);
}
private function configPath($file)
{
return PIWIK_INCLUDE_PATH . '/tests/resources/Config/' . $file;
}
}
AnalyzeArchiveTableTest::$fixture = new OneVisitorTwoVisits();

View file

@ -0,0 +1,22 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Test\Mock;
use Piwik\Plugins\Diagnostics\Diagnostic\Diagnostic;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResult;
class DiagnosticWithError implements Diagnostic
{
public function execute()
{
return array(
DiagnosticResult::singleResult('Error', DiagnosticResult::STATUS_ERROR, 'Comment'),
);
}
}

View file

@ -0,0 +1,22 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Test\Mock;
use Piwik\Plugins\Diagnostics\Diagnostic\Diagnostic;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResult;
class DiagnosticWithSuccess implements Diagnostic
{
public function execute()
{
return array(
DiagnosticResult::singleResult('Success', DiagnosticResult::STATUS_OK, 'Comment'),
);
}
}

View file

@ -0,0 +1,22 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Test\Mock;
use Piwik\Plugins\Diagnostics\Diagnostic\Diagnostic;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResult;
class DiagnosticWithWarning implements Diagnostic
{
public function execute()
{
return array(
DiagnosticResult::singleResult('Warning', DiagnosticResult::STATUS_WARNING, 'Comment'),
);
}
}

View file

@ -0,0 +1,37 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Test\Unit\Diagnostic;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResult;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResultItem;
class DiagnosticResultTest extends \PHPUnit_Framework_TestCase
{
public function test_getStatus_shouldReturnTheWorstStatus()
{
$result = new DiagnosticResult('Label');
$this->assertEquals(DiagnosticResult::STATUS_OK, $result->getStatus());
$result->addItem(new DiagnosticResultItem(DiagnosticResult::STATUS_WARNING));
$this->assertEquals(DiagnosticResult::STATUS_WARNING, $result->getStatus());
$result->addItem(new DiagnosticResultItem(DiagnosticResult::STATUS_ERROR));
$this->assertEquals(DiagnosticResult::STATUS_ERROR, $result->getStatus());
}
public function test_singleResult_shouldReturnAResultWithASingleItem()
{
$result = DiagnosticResult::singleResult('Label', DiagnosticResult::STATUS_ERROR);
$this->assertInstanceOf('Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResult', $result);
$this->assertEquals('Label', $result->getLabel());
$this->assertEquals(DiagnosticResult::STATUS_ERROR, $result->getStatus());
}
}

View file

@ -0,0 +1,47 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Test\Unit;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResult;
use Piwik\Plugins\Diagnostics\DiagnosticReport;
class DiagnosticReportTest extends \PHPUnit_Framework_TestCase
{
public function test_shouldComputeErrorAndWarningCount()
{
$report = new DiagnosticReport(
array(DiagnosticResult::singleResult('Error', DiagnosticResult::STATUS_ERROR, 'Comment')),
array(DiagnosticResult::singleResult('Warning', DiagnosticResult::STATUS_WARNING, 'Comment'))
);
$this->assertEquals(1, $report->getErrorCount());
$this->assertTrue($report->hasErrors());
$this->assertEquals(1, $report->getWarningCount());
$this->assertTrue($report->hasWarnings());
$report = new DiagnosticReport(array(), array());
$this->assertEquals(0, $report->getErrorCount());
$this->assertFalse($report->hasErrors());
$this->assertEquals(0, $report->getWarningCount());
$this->assertFalse($report->hasWarnings());
}
public function test_getAllResults()
{
$report = new DiagnosticReport(
array(DiagnosticResult::singleResult('Error', DiagnosticResult::STATUS_ERROR, 'Comment')),
array(DiagnosticResult::singleResult('Warning', DiagnosticResult::STATUS_WARNING, 'Comment'))
);
$this->assertCount(1, $report->getMandatoryDiagnosticResults());
$this->assertCount(1, $report->getOptionalDiagnosticResults());
$this->assertCount(2, $report->getAllResults());
}
}

View file

@ -0,0 +1,43 @@
<?php
/**
* Piwik - free/libre analytics platform
*
* @link http://piwik.org
* @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
*/
namespace Piwik\Plugins\Diagnostics\Test\Unit;
use Piwik\Plugins\Diagnostics\Diagnostic\DiagnosticResult;
use Piwik\Plugins\Diagnostics\DiagnosticService;
use Piwik\Plugins\Diagnostics\Test\Mock\DiagnosticWithError;
use Piwik\Plugins\Diagnostics\Test\Mock\DiagnosticWithSuccess;
use Piwik\Plugins\Diagnostics\Test\Mock\DiagnosticWithWarning;
class DiagnosticServiceTest extends \PHPUnit_Framework_TestCase
{
public function test_runDiagnostics()
{
$mandatoryDiagnostics = array(
new DiagnosticWithError(),
);
$optionalDiagnostics = array(
new DiagnosticWithWarning(),
new DiagnosticWithSuccess(),
);
$service = new DiagnosticService($mandatoryDiagnostics, $optionalDiagnostics, array());
$report = $service->runDiagnostics();
$results = $report->getAllResults();
$this->assertCount(3, $results);
$this->assertEquals('Error', $results[0]->getLabel());
$this->assertEquals(DiagnosticResult::STATUS_ERROR, $results[0]->getStatus());
$this->assertEquals('Warning', $results[1]->getLabel());
$this->assertEquals(DiagnosticResult::STATUS_WARNING, $results[1]->getStatus());
$this->assertEquals('Success', $results[2]->getLabel());
$this->assertEquals(DiagnosticResult::STATUS_OK, $results[2]->getStatus());
}
}

View file

@ -0,0 +1,39 @@
<?php
return array(
// Diagnostics for everything that is required for Piwik to run
'diagnostics.required' => array(
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\PhpVersionCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\DbAdapterCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\PhpExtensionsCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\PhpFunctionsCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\PhpSettingsCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\WriteAccessCheck'),
),
// Diagnostics for recommended features
'diagnostics.optional' => array(
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\FileIntegrityCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\TrackerCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\MemoryLimitCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\TimezoneCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\HttpClientCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\PageSpeedCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\GdExtensionCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\RecommendedExtensionsCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\RecommendedFunctionsCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\NfsDiskCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\CronArchivingCheck'),
DI\get('Piwik\Plugins\Diagnostics\Diagnostic\LoadDataInfileCheck'),
),
// Allows other plugins to disable diagnostics that were previously registered
'diagnostics.disabled' => array(),
'Piwik\Plugins\Diagnostics\DiagnosticService' => DI\object()
->constructor(DI\get('diagnostics.required'), DI\get('diagnostics.optional'), DI\get('diagnostics.disabled')),
'Piwik\Plugins\Diagnostics\Diagnostic\MemoryLimitCheck' => DI\object()
->constructorParameter('minimumMemoryLimit', DI\get('ini.General.minimum_memory_limit')),
'Piwik\Plugins\Diagnostics\Diagnostic\WriteAccessCheck' => DI\object()
->constructorParameter('tmpPath', DI\get('path.tmp')),
);

View file

@ -0,0 +1,8 @@
{
"Diagnostics": {
"ConfigFileTitle": "Konfigurační soubor",
"ConfigFileIntroduction": "Zde vidíte konfiguraci pro Piwik. Pokud Piwik běží v prostředí s vyvažováním zátěže, můžou se zobrazovaná data lišit podle toho, ze kterého serveru jsou natažena. Řádky se změněnou barvou pozadí značí změněné konfigurační hodnoty, které jsou specifikovány například v %1$s souboru.",
"HideUnchanged": "Pokud chcete vidět pouze změněné hodnoty, můžete %1$snezměněné hodnoty skrýt%2$s.",
"Sections": "Sekce"
}
}

View file

@ -0,0 +1,8 @@
{
"Diagnostics": {
"ConfigFileTitle": "Konfigurationsdatei",
"ConfigFileIntroduction": "Hier können Sie die Piwik Konfiguration einsehen. Sollten Sie Piwik auf lastverteilten Systemen einsetzen könnte diese Seite unterschiedlich sein, abhängig vom Server auf dem die Seite geladen wurde. Zeilen mit einer anderen Hintergrundfarbe sind geänderte Konfigurationswerte, die beispielsweise in der Datei %1$s definiert wurden.",
"HideUnchanged": "Falls Sie nur die geänderten Werte einsehen möchten können Sie %1$salle unveränderten Werte ausblenden%2$s.",
"Sections": "Sektionen"
}
}

View file

@ -0,0 +1,8 @@
{
"Diagnostics": {
"ConfigFileTitle": "Αρχείο ρυθμίσεων",
"ConfigFileIntroduction": "Εδώ μπορείτε να δείτε τις ρυθμίσεις του Piwik. Αν εκτελείτε το Piwik σε περιβάλλον με διαμοιρασμό φόρτου, η σελίδα μπορεί να είναι διαφορετική, ανάλογα από ποιο διακομιστή έχει φορτωθεί. Οι γραμμές με διαφορετικό χρώμα υποβάθρου είναι οι τιμές ρυθμίσεων που άλλαξαν για παράδειγμα στο αρχείο ρυθμίσεων %1$s.",
"HideUnchanged": "Αν επιθυμείτε να δείτε μόνο τις τιμές που άλλαξαν, μπορείτε να %1$sαποκρύψετε τις τιμές που παρέμειναν ίδιες%2$s.",
"Sections": "Τμήματα"
}
}

View file

@ -0,0 +1,8 @@
{
"Diagnostics": {
"ConfigFileTitle": "Config file",
"ConfigFileIntroduction": "Here you can view the Piwik configuration. If you are running Piwik in a load balanced environment the page might be different depending from which server this page is loaded. Rows with a different background color are changed config values that are specified for example in the %1$s file.",
"HideUnchanged": "If you want to see only changed values you can %1$shide all unchanged values%2$s.",
"Sections": "Sections"
}
}

View file

@ -0,0 +1,6 @@
{
"Diagnostics": {
"ConfigFileTitle": "File di configurazione",
"Sections": "Sezioni"
}
}

View file

@ -0,0 +1,8 @@
{
"Diagnostics": {
"ConfigFileTitle": "Arquivo de configuração",
"ConfigFileIntroduction": "Aqui você pode ver a configuração do Piwik. Se você estiver executando Piwik em um ambiente de balanceamento de carga a página pode ser diferente, dependendo de qual servidor esta página é carregada. Linhas com uma cor de fundo diferente são alterados os valores de configuração que são especificadas por exemplo, no arquivo %1$s.",
"HideUnchanged": "Se você quiser ver apenas valores alterados você pode %1$socultar todos os valores inalterados%2$s.",
"Sections": "Seções"
}
}

View file

@ -0,0 +1,5 @@
{
"Diagnostics": {
"ConfigFileTitle": "Konfigurationsfil"
}
}

View file

@ -0,0 +1,3 @@
{
"description": "Performs diagnostics to check that Piwik is installed and runs correctly."
}

View file

@ -0,0 +1,22 @@
.diagnostics.configfile {
.custom-value {
background-color: @theme-color-background-tinyContrast;
}
.defaultValue {
font-style: italic;
}
td.name {
max-width: 330px;
word-wrap: break-word;
width: 25%;
}
td.value {
word-wrap: break-word;
max-width: 400px;
width: 25%;
}
}

View file

@ -0,0 +1,55 @@
{% extends 'admin.twig' %}
{% macro humanReadableValue(value) %}
{% if value is false %}
false
{% elseif value is true %}
true
{% elseif value is null %}
{% elseif value is emptyString %}
''
{% else %}
{{ value|join(', ') }}
{% endif %}
{% endmacro %}
{% block content %}
<h2 piwik-enriched-headline>{{ 'Diagnostics_ConfigFileTitle'|translate }}</h2>
<p>
{{ 'Diagnostics_ConfigFileIntroduction'|translate('<code>"config/config.ini.php"</code>')|raw }}
{{ 'Diagnostics_HideUnchanged'|translate('<a ng-click="hideGlobalConfigValues=!hideGlobalConfigValues">', '</a>')|raw }}
<h3>{{ 'Diagnostics_Sections'|translate }}</h3>
{% for category, values in allConfigValues %}
<a href="#{{ category|e('html_attr') }}">{{ category }}</a><br />
{% endfor %}
</p>
<table class="simple-table diagnostics configfile">
<tbody>
{% for category, configValues in allConfigValues %}
<tr><td colspan="3"><a name="{{ category|e('html_attr') }}"></a><h3>{{ category }}</h3></td></tr>
{% for key, configEntry in configValues %}
<tr {% if configEntry.isCustomValue %}class="custom-value"{% else %}ng-hide="hideGlobalConfigValues"{% endif %}>
<td class="name">{{ key }}{% if configEntry.value is iterable %}[]{% endif %}</td>
<td class="value">
{{ _self.humanReadableValue(configEntry.value) }}
</td>
<td class="description">
{{ configEntry.description }}
{% if (configEntry.isCustomValue or configEntry.value is null) and configEntry.defaultValue is not null %}
{% if configEntry.description %}<br />{% endif %}
{{ 'General_Default'|translate }}:
<span class="defaultValue">{{ _self.humanReadableValue(configEntry.defaultValue) }}<span>
{% endif %}
</td>
</tr>
{% endfor %}
{% endfor %}
</tbody>
</table>
{% endblock %}