Skip to content
Snippets Groups Projects
Commit 3028db50 authored by Stephane Bouvry's avatar Stephane Bouvry
Browse files

Commande pour tester les connections (en cours)

parent 6b7c4378
No related branches found
No related tags found
No related merge requests found
Pipeline #30490 passed
......@@ -9,6 +9,7 @@
namespace Oscar\Command;
use Doctrine\DBAL\DriverManager;
use Doctrine\ORM\EntityManager;
use Doctrine\ORM\Tools\SchemaValidator;
use Monolog\Logger;
......@@ -18,6 +19,7 @@ use Oscar\OscarVersion;
use Oscar\Service\ConfigurationParser;
use Oscar\Service\OscarConfigurationService;
use Oscar\Service\OscarUserContext;
use Symfony\Component\Console\Input\InputArgument;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Console\Style\SymfonyStyle;
......@@ -25,12 +27,13 @@ use Symfony\Component\Yaml\Parser;
class OscarCheckConnectionCommand extends OscarCommandAbstract
{
protected static $defaultName = 'check:config';
protected static $defaultName = 'check:connection';
protected function configure()
{
$this
->setDescription("Vérification de la configuration");
->setDescription("Vérification de la configuration")
->addArgument('name', InputArgument::OPTIONAL, 'Nom de la connection', null);
}
/**
......@@ -49,436 +52,41 @@ class OscarCheckConnectionCommand extends OscarCommandAbstract
return $this->getServicemanager()->get('Logger');
}
protected function checkConnectorPerson(InputInterface $input, OutputInterface $output)
{
$io = new SymfonyStyle($input, $output);
$io->title("Configuration du connecteur PERSON");
/** @var OscarConfigurationService $config */
$config = $this->getOscarConfiguration();
$connectors = $config->getConfiguration('connectors.person');
foreach ($connectors as $key => $params) {
$io->text("-------------------------------------------------------");
$io->text(sprintf("# Configuration : <bold>%s</bold>", $key));
// Class
$io->text(sprintf("class: <bold>%s</bold>", $params['class']));
$io->text("---");
// Options du connecteur
$fileYml = $params['params'];
/** @var AbstractConnectorOscar $class */
$class = new $params['class'];
if ($this->checkPath($io, $fileYml, "Fichier de configuration du connector", 'r')) {
$class->init($this->getServicemanager(), $fileYml, $key);
$parser = new Parser();
$paramsPhp = $parser->parse(file_get_contents($fileYml));
foreach ($paramsPhp as $paramKey => $paramValue) {
$io->text(sprintf(' + %s : <bold>%s</bold>', $paramKey, $paramValue));
}
$io->write(sprintf('* Accès au connecteur <bold>%s</bold>', $paramsPhp['url_persons']));
if ($class->checkAccess()) {
$io->write(" <green>OK</green>");
} else {
$io->write(" <error>ERROR !</error>");
}
$io->newLine();
}
$io->text("-------------------------------------------------------");
}
}
protected function checkConnectorOrganization(InputInterface $input, OutputInterface $output)
{
$io = new SymfonyStyle($input, $output);
$io->title("Configuration du connecteur ORGANIZATION");
/** @var OscarConfigurationService $config */
$config = $this->getOscarConfiguration();
$connectors = $config->getConfiguration('connectors.organization');
foreach ($connectors as $key => $params) {
$io->text(sprintf("Configuration : <bold>%s</bold>", $key));
// Class
$io->text(sprintf("class: <bold>%s</bold>", $params['class']));
// Options du connecteur
$fileYml = $params['params'];
/** @var AbstractConnectorOscar $class */
$class = new $params['class'];
if ($this->checkPath($io, $fileYml, "Fichier de configuration du connector", 'r')) {
$class->init($this->getServicemanager(), $fileYml, $key);
$parser = new Parser();
$paramsPhp = $parser->parse(file_get_contents($fileYml));
foreach ($paramsPhp as $paramKey => $paramValue) {
$io->text(sprintf(' + %s : <bold>%s</bold>', $paramKey, $paramValue));
}
$io->write(sprintf('* Accès au connecteur <bold>%s</bold>', $paramsPhp['url_organization']));
if ($class->checkAccess()) {
$io->write(" <green>OK</green>");
} else {
$io->write(" <error>ERROR !</error>");
}
$io->newLine();
}
}
}
protected function execute(InputInterface $input, OutputInterface $output): int
{
$name = $input->getArgument('name');
$config = $this->getServicemanager()->get('Config');
$this->addOutputStyle($output);
/** @var OscarUserContext $oscaruserContext */
$oscaruserContext = $this->getServicemanager()->get(OscarUserContext::class);
$this->getLogger()->info("[COMMAND] check:config");
$io = new SymfonyStyle($input, $output);
$io->title("Vérification de la configuration");
/** @var OscarConfigurationService $oscarConfig */
$oscarConfig = $this->getServicemanager()->get(OscarConfigurationService::class);
$rootPath = __DIR__ . '/../../../../../';
$configPath = 'config/autoload/local.php';
$configPathReal = realpath($rootPath . $configPath);
$configEditablePath = 'config/autoload/oscar-editable.yml';
$configEditablePathReal = realpath($rootPath . $configEditablePath);
$io->writeln("N°Version : <bold>" . OscarVersion::getBuild() . "</bold>");
$io->writeln("Configuration : <bold>" . $configPathReal . "</bold>");
$io->writeln("System : <bold>" . php_uname() . "</bold>");
$io->section("PHP Requirements : ");
//php_ini_loaded_file
$io->write(
" - PHP version : <bold>" . PHP_MAJOR_VERSION . '.' . PHP_MINOR_VERSION . '.' . PHP_RELEASE_VERSION . "</bold> (<bold>" . phpversion(
) . "</bold>)"
);
if (PHP_VERSION_ID < 70000) {
$io->error('Major version required !');
return self::FAILURE;
} else {
$io->write("<green>OK</green>\n");
}
$io->writeln("\n - php.ini ");
$io->writeln(php_ini_loaded_file());
$io->section("Modules");
$modulesRequires = [
'bz2',
'curl',
'fileinfo',
'gd',
'gearman',
'iconv',
'json',
'ldap',
'mbstring',
'openssl',
'pdo_pgsql',
'posix',
'Reflection',
'session',
'xml',
'zip'
];
foreach ($modulesRequires as $moduleName) {
$row[] = $this->checkModule($moduleName, $io);
}
$io->table(['Modules PHP', 'Version', 'Statut'], $row);
$io->section(" OSCAR configuration : ");
$io->write(" - Configuration LOCAL <bold>$configPath</bold> : ");
if ($configPathReal && !file_exists($configPathReal)) {
$io->error("ERROR : Le fichier de configuration '$configPath' n'existe pas/n'est pas accessible");
return self::FAILURE;
}
$io->writeln("<green>OK</green>");
$io->write(" - Configuration éditable (<bold>$configEditablePath</bold>) : ");
if ($configEditablePathReal && !file_exists($configEditablePathReal)) {
$io->error("Le fichier de configuration n'existe pas/n'est pas accessible");
return self::FAILURE;
}
if (!is_writable($configEditablePath)) {
$io->error("Le fichier de configuration n'est pas éditable");
return self::FAILURE;
}
$io->writeln("<green>OK</green>");
$logPath = $oscarConfig->getLoggerFilePath();
$io->write(" - Fichier de LOG (<bold>$logPath</bold>) : ");
if (!is_writable($logPath)) {
$io->error("Le fichier de log n'est pas éditable");
return self::FAILURE;
}
$io->writeln("<green>OK</green>");
$config = new ConfigurationParser(
$this->getServicemanager()->get(OscarConfigurationService::class)->getConfigArray()
);
$em = $this->getServicemanager()->get(EntityManager::class);
try {
$io->write(" - Accès à la base de données ");
$io->write($config->getConfiguration('doctrine.connection.orm_default.params.host'));
$io->write(" ... ");
if ($em->getConnection()->isConnected()) {
$io->writeln("<green>OK</green>");
}
$validator = new SchemaValidator($em);
$errors = $validator->validateMapping();
$io->write(" - Modèle de donnée ");
if (count($errors) > 0) {
$io->warning("Obsolète");
foreach ($errors as $error) {
$io->error(" - " . print_r($error));
}
$io->error("EXECUTER : php vendor/bin/doctrine-module orm:schema-tool:update --force");
$database_config = $config['doctrine']['connection'];
$available_connections = array_keys($database_config);
if ($name != null && !in_array($name, $available_connections)) {
$io->error("Connection '$name' n'existe pas'");
return self::FAILURE;
} else {
$io->writeln("<green>OK</green>");
}
} catch (\Exception $e) {
$io->writeln("ERROR DB : " . $e->getMessage());
return self::FAILURE;
}
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// DOSSIERS / FICHIERS
try {
$io->section("Emplacements des fichiers/Dossiers : ");
$pathDocuments = $config->getConfiguration('oscar.paths.document_oscar');
$this->checkPath($io, $pathDocuments, "Stoquage des documents > ACTIVITÉS");
$pathDocuments = $config->getConfiguration('oscar.paths.document_admin_oscar');
$this->checkPath($io, $pathDocuments, "Stoquage des documents > ADMINISTRATIFS");
$pathDocuments = $config->getConfiguration('oscar.paths.timesheet_modele');
$this->checkPath($io, $pathDocuments, "Modèle de document > FEUILLE DE TEMPS");
$pathDocuments = $config->getConfiguration('oscar.mailer.template');
$this->checkPath($io, $pathDocuments, "Modèle de mail > TEMPLATE");
$pathDocuments = $config->getConfiguration('oscar.pcru.files_path');
$this->checkPath($io, $pathDocuments, "Documents temporaires PCRU");
} catch (OscarException $e) {
$io->error(sprintf("Configuration manquante : %s", $e->getMessage()));
return self::FAILURE;
}
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// MAILER
try {
$io->section(" ### Configuration du mailer : ");
$urlAbsolute = $config->getConfiguration('oscar.urlAbsolute');
$io->write(" - URL absolue (Utilisée pour forger les liens) : ");
if ($urlAbsolute == "http://localhost:8080") {
$io->writeln('<id> !DEV! ' . $urlAbsolute . '</id>');
} else {
$io->writeln($urlAbsolute);
}
$io->write(" - Transport : ");
$typeTransport = $config->getConfiguration('oscar.mailer.transport.type');
$typeTransportValid = in_array($typeTransport, ['sendmail', 'smtp', 'file']);
if ($typeTransportValid) {
$io->writeln("<green>$typeTransport</green>");
switch ($typeTransport) {
case 'sendmail' :
$io->writeln("Attention, l'utilisation de SENDMAIL n'est pas testée dans cette version");
//
break;
case 'smtp' :
$io->writeln("Attention, l'utilisation d'un serveur SMTP n'est pas testée dans cette version");
//
break;
case 'file' :
$pathDocuments = $config->getConfiguration('oscar.mailer.transport.path');
$this->checkPath($io, $pathDocuments, "Dossier où sont archivés les mails (DEBUG)");
break;
}
else {
if ($name == null) {
$conn = $database_config;
} else {
$io->writeln("Type de transport inconnu '$typeTransport''");
$conn = ["$name" => $database_config[$name]];
}
$io->writeln("");
} catch (OscarException $e) {
$io->error(sprintf("Configuration manquante : %s", $e->getMessage()));
return self::FAILURE;
}
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// MOTEUR de RECHERCHE
$io->section(" ### Système d'indexation des activités : ");
foreach ($conn as $c_name=>$c_conf) {
$io->info($c_name);
$co = DriverManager::getConnection($c_conf['params']);
try {
$searchClass = $config->getConfiguration('oscar.strategy.activity.search_engine.class');
// ELASTIC SEARCH
if ($searchClass == 'Oscar\Strategy\Search\ElasticActivitySearch') {
$io->write(" * Moteur Elastic Search ");
$nodesUrl = $config->getConfiguration('oscar.strategy.activity.search_engine.params');
foreach ($nodesUrl[0] as $url) {
$io->write("Noeud $url ");
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
$infos = curl_exec($curl);
if (($error = curl_error($curl))) {
$io->write("<error>Error : " . $error . "</error>");
if( $co->connect() ) {
$io->success("Connection à '$c_name' réussie");
} else {
$io->write("<green>OK (Response 200)</green>");
}
curl_close($curl);
}
} // LUCENE
elseif ($searchClass == ActivityZendLucene::class) {
$params = $config->getConfiguration('oscar.strategy.activity.search_engine.params');
$this->checkPath($params[0], "Dossier pour l'index de recherche LUCENE");
} else {
$io->warning(" ~ INDEXEUR : Système de recherche non testable...");
}
} catch (OscarException $e) {
$io->error(sprintf(" ! INDEXEUR : Configuration du système de recherche incomplet : %s", $e->getMessage()));
return self::FAILURE;
}
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// CONNECTORS
try {
$this->checkConnectorOrganization($input, $output);
} catch (OscarException $e) {
$io->warning(sprintf(" ~ CONNECTOR > ORGANIZATIONS : Pas de connecteur person : %s", $e->getMessage()));
}
try {
$this->checkConnectorPerson($input, $output);
} catch (OscarException $e) {
echo $e->getTraceAsString();
$io->warning(sprintf(" ~ CONNECTOR > PERSONS : Pas de connecteur person : %s", $e->getMessage()));
}
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
///
/// GEARMMAN
///
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
$io->section(" ### GEARMAN : ");
// On teste la présence du worker
$oscarWorkerFile = __DIR__ . '/../../../../../config/oscarworker.service';
if (!file_exists($oscarWorkerFile)) {
$io->error("Le fichier OscarWorker est absent (config/oscarworker.service)");
return self::FAILURE;
}
$io->write(sprintf("* Envoi d'un job 'HELLO' à Gearman sur '%s' : ", $oscarConfig->getGearmanHost()));
$client = new \GearmanClient();
try {
$client->addServer($oscarConfig->getGearmanHost());
$client->setTimeout(1000);
if (!($response = @$client->doHigh(
'hello',
json_encode(['message' => 'Check Config Oscar']),
'check-config'
))) {
$io->error(
"LE WORKER NE RÉAGIT PAS, Vérifiez qu'il est bien lancé, si vous avez réalisé une mise à jour, pensez à relancer le service.\n Gearman a répondu : " . $client->error(
)
);
return self::FAILURE;
} else {
$io->writeln("OscarWorker a répondu : '<green>$response</green>'");
$io->warning("Connection refusée");
}
} catch (\Exception $e) {
$io->error(
"GEARMAN FAIL, Impossible de se connecter au serveur Gearman '" . $oscarConfig->getGearmanHost(
) . "' : \n Erreur : " . $client->error()
);
return self::FAILURE;
}
return self::SUCCESS;
}
protected function checkPath(SymfonyStyle $io, $path, $text, $level = 'error', $allowed = 'rw')
{
$io->write(" - Path <bold>$path</bold> : ");
if (!file_exists($path)) {
$io->writeln("<error>Le chemin n'existe pas / inaccessible</error>");
return false;
}
if (!is_readable($path)) {
$io->writeln("<error>Chemin inaccessible en lecture.</error>");
return false;
}
if (strpos($allowed, 'w') > -1 && !is_writable($path)) {
$io->writeln("<error>Chemin inacessible en écriture.</error>");
return false;
$io->error($e->getMessage());
}
$io->writeln("<green>OK!</green>");
return true;
}
protected function checkModule($module, SymfonyStyle $io, $level = 'error')
{
$badOut = $level == 'warn' ? 'warning' : 'error';
$msg = $level == 'warn' ? "WARNING" : "ERROR";
$out = [];
$out[] = "<bold>$module</bold>";
$out[] = phpversion($module) ?: '???';
if (!extension_loaded($module)) {
$out[] = "<error>Missing $module !!!</error>";
} else {
$out[] = "<green>Installed</green>";
}
return $out;
return self::FAILURE;
}
}
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment