setName('security')
->setDescription('Capable of running various Security checks')
->setHelp('The security runs various security checks on your Grav site');
$this->source = getcwd();
}
protected function serve()
{
/** @var Grav $grav */
$grav = Grav::instance();
$grav->setup();
$grav['uri']->init();
$grav['config']->init();
$grav['debugger']->enabled(false);
$grav['plugins']->init();
$grav['themes']->init();
$grav['twig']->init();
$grav['pages']->init();
$this->progress = new ProgressBar($this->output, \count($grav['pages']->routes()) - 1);
$this->progress->setFormat('Scanning %current% pages [%bar%] %percent:3s%% %elapsed:6s%');
$this->progress->setBarWidth(100);
$io = new SymfonyStyle($this->input, $this->output);
$io->title('Grav Security Check');
$output = Security::detectXssFromPages($grav['pages'], false, [$this, 'outputProgress']);
$io->newline(2);
if (!empty($output)) {
$counter = 1;
foreach ($output as $route => $results) {
$results_parts = array_map(function($value, $key) {
return $key.': \''.$value . '\'';
}, array_values($results), array_keys($results));
$io->writeln($counter++ .' - ' . $route . ' → ' . implode(', ', $results_parts) . '');
}
$io->error('Security Scan complete: ' . \count($output) . ' potential XSS issues found...');
} else {
$io->success('Security Scan complete: No issues found...');
}
$io->newline(1);
}
/**
* @param array $args
*/
public function outputProgress($args)
{
switch ($args['type']) {
case 'count':
$steps = $args['steps'];
$freq = (int)($steps > 100 ? round($steps / 100) : $steps);
$this->progress->setMaxSteps($steps);
$this->progress->setRedrawFrequency($freq);
break;
case 'progress':
if (isset($args['complete']) && $args['complete']) {
$this->progress->finish();
} else {
$this->progress->advance();
}
break;
}
}
}