New file |
0,0 → 1,600 |
<?php |
/** |
* Classe Commun.php est une classe abstraite qui contient les méthodes de base communes à tous les |
* sous-services des projets. |
* |
* Encodage en entrée : utf8 |
* Encodage en sortie : utf8 |
* @package eflore-projets |
* @author Jennifer DHÉ <jennifer.dhe@tela-botanica.org> |
* @author Delphine CAUQUIL <delphine@tela-botanica.org> |
* @author Jean-Pascal MILCENT <jpm@tela-botanica.org> |
* @license GPL v3 <http://www.gnu.org/licenses/gpl.txt> |
* @license CECILL v2 <http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt> |
* @version 1.0 |
* @copyright 1999-2011 Tela Botanica (accueil@tela-botanica.org) |
*/ |
|
abstract class Commun { |
|
/** Objet Bdd. */ |
private $Bdd = null; |
/** Objet Rest Client. */ |
private $RestClient = null; |
|
/** par défaut : configuration du projet, section [NomDuService] */ |
protected $config; |
|
/** Contients les paramètres. Doit remplacer table_param. */ |
protected $parametres = array(); |
/** Contients les ressources. Doit remplacer table_ressources. */ |
protected $ressources = array(); |
/** Le nom du service courrant. */ |
protected $serviceNom = null; |
|
//Classe commune à tous les services web d'un projet. Contient par exemple les fonctions permettant de |
//renvoyer la réponse http... |
protected $entete_http; // Entete de la réponse correspondant au code de réponse de la requete http */ |
protected $corps_http; // Tableau de résultat à retourner au format json ou la description de l'erreur si elle existe */ |
protected $service; // Nom du service appelé |
/** Stocke la version du projet demandée dans la requete |
* - "*" : (/#projet/* /meta-donnees) Renvoi les meta-données de toutes les versions du projet |
* - "numero de la version" : (/#projet/2.00/meta-donnees) Renvoi les meta-données de la version 2.00 du projet */ |
protected $version_projet = '+'; |
protected $table_version; //Stocke les noms des tables de toutes les versions du projet disponibles |
/** tableau contenant tous les champs d'une table (est rempli par la fonction Commun::recupererNomChamp($table)) */ |
protected $champs_table = array(); |
|
public function __construct($bdd = null, $config = null) { |
$this->Bdd = is_null($bdd) ? $this->getBdd() : $bdd; |
$this->config = is_null($config) ? Config::get($this->serviceNom) : $config; |
$this->init(); |
} |
|
// ajustements post-constructeur |
protected function init() {} |
|
public function consulter($ressources, $parametres) { |
$this->ressources = $ressources; |
$this->parametres = $parametres; |
$this->chargerNomDuService(); |
|
$this->traiterParametres(); |
$this->traiterVersionProjet(); |
|
$resultats = ''; |
foreach ($this->table_version as $version) { |
$this->table = $version; //on stocke le nom de la table correspondant à la version du projet en cours |
$this->recupererNomChamp($this->table); //on récupère les noms des champs disponibles (Ds Commun.php) |
$this->traiterRessources(); //dans CommunNomsTaxons.php |
$requete = $this->assemblerLaRequete();// dans Noms ou Taxons... |
$resultat = $this->getBdd()->recupererTous($requete . ' -- ' . __FILE__ . ':' . __LINE__ . ' (' .$this->table . ')'); |
$versionResultat = $this->traiterResultat($resultat, $version, $requete); |
if (count($this->table_version) > 1) { |
$resultats[$version] = $versionResultat; |
} else { |
$resultats = $versionResultat; |
} |
} |
|
return $resultats; |
} |
|
private function chargerNomDuService() { |
$this->serviceNom = get_class($this); |
} |
|
public function traiterResultat($resultat, $version) { |
$versionResultat = null; |
if ($resultat == '') { |
//cas ou la requete comporte des erreurs |
$message = 'La requête SQL formée comporte une erreur!'; |
$code = RestServeur::HTTP_CODE_RESSOURCE_INTROUVABLE; |
throw new Exception($message, $code); |
} elseif ($resultat) { |
$versionResultat = $this->retournerResultatFormate($resultat, $version); |
} else { |
$message = 'Les données recherchées sont introuvables.'; |
$code = RestServeur::HTTP_CODE_RESSOURCE_INTROUVABLE; |
throw new Exception($message, $code); |
} |
return $versionResultat; |
} |
|
//+------------------------------------------------------------------------------------------------------+ |
// Méthodes concernant les paramètres |
/** |
* Permet de récupérer une liste des noms des champs de la table passée en paramètre |
* @param $table : Nom de la table dont on souhaite connaitre les champs |
*/ |
public function recupererNomChamp($table) { |
$resultat = @$this->getBdd()->recupererTous('SHOW FIELDS FROM '.$table); |
if (!$resultat) { |
$m = "La table recherchée n'existe pas"; |
$this->renvoyerErreur(RestServeur::HTTP_CODE_RESSOURCE_INTROUVABLE, $m); |
} |
|
foreach ($resultat as $info) $this->champs_table[] = $info['Field']; |
} |
|
/** |
* Fonction permettant de creer la table dont le nom est passé en paramètre (champs_api, champs_bdtfx, |
* correspondance_champs...). Les données de chaque table sont présentes dans le fichier de configuration config.ini |
* @param String $table : Peut contenir plusieurs nom de table dont on souhaite récupérer les données : table,table,table. |
* Ex : recupererTableConfig('champs_api,champs_bdtfx') |
*/ |
public function recupererTableConfig($table) { |
$tables = explode(',', $table); |
foreach ($tables as $tab) { |
$tableau = explode(',', Config::get($tab)); |
$tableau = array_map('trim', $tableau); |
foreach ($tableau as $champ) { |
list($code, $rang) = explode('=', $champ); |
$tab_tampon[$code] = $rang; |
} |
$this->$tab = $tab_tampon; |
$tab_tampon = array(); |
} |
} |
|
public function renvoyerErreur($entete, $message) { |
throw new Exception($message, $entete); |
} |
|
/** |
* Permet de remplir la variable version_projet et de retirer cette donnée du tableau des ressources |
* @param $ressources |
*/ |
public function traiterVersionProjet() { |
if (isset($this->parametres['version.projet'])) { |
if (preg_match('/^[0-9]+(?:[._][0-9]+|)$/', $this->parametres['version.projet'])) { |
$this->version_projet = $this->parametres['version.projet']; |
$this->version_projet = 'v'.str_replace('.', '_', $this->version_projet); |
} else { |
$this->version_projet = $this->parametres['version.projet']; |
} |
} |
//si la liste des noms est demandée pr toutes les versions, on affiche seulement la dernière version : |
if ($this->version_projet == '*' && $this->ressources == array()) { |
$message = "L'affichage de plusieurs versions ne fonctionne que pour les ressources de type /ressources/#id"; |
$code = RestServeur::HTTP_CODE_MAUVAISE_REQUETE; |
throw new Exception($message, $code); |
} |
//on recupère les versions du projet disponible dans la table des meta-donnees (utilisation service MetaDonnees) |
$table_num_version = $this->recupererVersionDisponible(); |
//on recupere la liste des noms des tables de la bdd correspondant aux differentes versions du projet en fct de la ou les versions demandées |
$this->recupererListeNomTablePrChaqueVersion($table_num_version); |
} |
|
/** |
* Recupération des versions disponibles par appel du service metaDonnees |
* Verification de l'existance du service recherché dans la requete (si précisé : hors *) |
* @return array : tableau contenant le numéro de chaque version disponible |
*/ |
public function recupererVersionDisponible() { |
$versions_dispo = ''; |
$req_version = 'SELECT version FROM '.Config::get('bdd_table_meta'); |
$res_version = $this->getBdd()->recupererTous($req_version); |
if ($res_version == '') { //cas ou la requete comporte des erreurs |
$e = "La requête SQL de versionnage formée comporte une erreur : $req_version"; |
$this->renvoyerErreur(RestServeur::HTTP_CODE_RESSOURCE_INTROUVABLE, $e); |
} elseif ($res_version) { |
foreach ($res_version as $version) { |
$versions_dispo[] = $version['version']; |
} |
} else { |
$m = 'Versions introuvables dans la table des méta-données'; |
$this->renvoyerErreur(RestServeur::HTTP_CODE_RESSOURCE_INTROUVABLE, $m); |
} |
return $versions_dispo; |
} |
|
public function recupererListeNomTablePrChaqueVersion($table_num_version) { |
switch ($this->serviceNom) { |
case 'Ontologies' : |
$prefixe_table = 'bdd_table_ontologies'; |
break; |
default: |
$prefixe_table = 'bdd_table'; |
} |
switch ($this->version_projet) { |
case '+' : |
$derniere_version = $table_num_version[count($table_num_version) - 1]; |
$this->table_version[] = Config::get($prefixe_table).'_v'.str_replace('.', '_', $derniere_version); |
break; |
case '*' : |
foreach ($table_num_version as $num_version) { |
$this->table_version[] = Config::get($prefixe_table).'_v'.str_replace('.', '_', $num_version); |
} |
break; |
default : |
$this->table_version[] = Config::get($prefixe_table).'_'.$this->version_projet; |
break; |
} |
} |
|
//valeur * signifie pas de limites |
public function definirNavigationLimite($valeur){ |
if (isset($this->parametres['navigation.limite']) ) { |
if ((preg_match('/^([0-9]+)$/', $valeur) && $valeur != 0 ) || $valeur == '*' ){ |
$this->limite_requete['limite'] = $valeur; |
} else { |
$e = "Erreur : valeur erronnée pour le paramètre navigation.limite."; |
throw new Exception($e, RestServeur::HTTP_CODE_MAUVAISE_REQUETE); |
} |
} |
} |
|
public function definirNavigationDepart($valeur){ |
if (isset($this->parametres['navigation.depart'])) { |
if(preg_match('/^([0-9]+)$/', $valeur)){ |
$this->limite_requete['depart'] = $valeur; |
} else { |
$e = "Erreur : valeur erronnée pour le paramètre navigation.depart."; |
throw new Exception($e, RestServeur::HTTP_CODE_MAUVAISE_REQUETE); |
} |
} else { |
$e = "indiquez également la valeur pour le paramètre navigation.limite."; |
throw new Exception($e, RestServeur::HTTP_CODE_MAUVAISE_REQUETE); |
} |
} |
/** |
* Est appelée pour former l'url complete des resultats precedants ou suivants. |
* @param int : Permet de connaitre le nombre de noms obtenus par la requete |
* @return string Retourne l'url complete des resultats precedents ou suivant sous la forme d'un tableau |
*/ |
public function formulerUrl($nb_resultat, $id = null) { |
$url = array(); |
$debut_url = Config::get('url_service').$id.'?'; |
//on recréé l'url sans les parametres de navigation qui seront rajoutés ci-apres. On les enlève dc de la table des parametres |
foreach($this->parametres as $cle => $val) { |
$param_url[str_replace('_', '.', $cle)] = $val; |
} |
|
$this->recupererLesLimitesSuivantes($nb_resultat, $param_url); |
if (isset($param_url['navigation.depart']) && isset($param_url['navigation.limite'])) { |
$url['suivant'] = $debut_url.http_build_query($param_url); |
} |
|
$this->recupererLesLimitesPrecedentes($param_url); |
if (isset($param_url['navigation.depart']) && isset($param_url['navigation.limite'])) { |
$url['precedent'] = $debut_url.http_build_query($param_url); |
} |
return $url; |
} |
|
public function supprimerNavigation(&$param_url) { |
unset($param_url['navigation.depart']); |
unset($param_url['navigation.limite']); |
} |
|
/** |
* Description : |
* Permet de former les limites de la requete retournant les résultats suivants. |
* Cette url sera afficher dans l'entete de la reponse retournée en format JSON (retour.format=defaut). |
* @param int : $nb_resultat : Permet de connaitre le nombre de résultats obtenus par la requete |
* @return string : la fin de l'url decrivant les limites des resultats suivants. Si aucun résultats ne suient, |
* une chaine de caractère vide est retournée |
*/ |
public function recupererLesLimitesSuivantes($nb_resultat, &$param_url_suiv) { |
$this->supprimerNavigation($param_url); |
$depart = $this->limite_requete['depart']; |
$limite = $this->limite_requete['limite']; |
$depart_suivant = $depart + $limite; |
$limite_suivant = $limite; |
if ($nb_resultat > $depart_suivant) { |
$param_url_suiv['navigation.depart'] = $depart_suivant; |
$param_url_suiv['navigation.limite'] = $limite_suivant; |
} else { |
$param_url_suiv['navigation.depart'] = null; |
$param_url_suiv['navigation.limite'] = null; |
} |
} |
|
/** |
* Description : |
* Permet de former les limites de la requete retournant les résultats precedents. |
* Cette url sera afficher dans l'entete de la taxons/105reponse retournée en format JSON (retour.format=defaut) |
* @return string : la fin de l'url decrivant les limites des resultats precedents. |
* Si aucun résultats ne precedent, une chaine de caractère vide est retournée |
*/ |
public function recupererLesLimitesPrecedentes(&$param_url) { |
$this->supprimerNavigation($param_url); |
$depart = $this->limite_requete['depart']; |
$limite = $this->limite_requete['limite']; |
if ($depart == 0) { |
$url_precedente = ''; |
} else { |
if (($depart - $limite) < 0) { |
$depart_precedent = 0; |
} else { |
$depart_precedent = $depart - $limite; |
} |
$param_url['navigation.depart'] = $depart_precedent; |
$param_url['navigation.limite'] = $limite; |
} |
} |
|
static function getDureeCache() { |
$dureecache = 0; |
$dureecache = Config::get('dureecache'); |
if ($dureecache == null || !is_numeric($dureecache) || $dureecache < 0) { |
$dureecache = 0; |
} |
return (int) $dureecache; |
} |
|
public function ajouterHref($service, $val) { |
// http://tela-botanica.org/service:eflore:0.1/[projet]/[version_projet]/[service]/[ressource]:[valeur] |
if ($this->version_projet == '+') { |
$url = Config::get('url_service_base').Config::get('nom_projet').'/'.$service.'/'.$val; |
} else { |
$url = Config::get('url_service_base').Config::get('nom_projet').'/'.$service.'/'.$val.'?version.projet='.ltrim($this->version_projet, 'v'); |
} |
return $url; |
} |
|
static function s_ajouterHref($service, $val, $version_projet = '') { |
// http://tela-botanica.org/service:eflore:0.1/[projet]/[version_projet]/[service]/[ressource]:[valeur] |
return Config::get('url_service_base').Config::get('nom_projet').'/'.$service.'/'.$val . ($version_projet != '+') ? ('?version.projet='.ltrim($version_projet, 'v')) : ''; |
} |
|
public function ajouterHrefAutreProjet($service, $ressource, $valeur, $projet = null, $param = null) { |
//on enleve les GA et Co, les meta ou les "_" |
$this->transliterer($service, $valeur); |
//on définit les nom des projets, des services et des ressources de l'url (dans les méta-donnees) |
$tab = array( |
'langue' => array('service' => 'langues', 'projet' => 'iso-639-1', 'ressource' => ''), |
'couverture_spatiale' => array('service' => 'zone-geo', 'projet' => 'iso-3166-1', 'ressource' => ''), |
'type' => array('service' => 'ontologies', 'projet' => 'eflore', 'ressource' => 'contactType:'), |
'datum' => array('service' => 'ontologies', 'projet' => 'eflore', 'ressource' => 'datum:') |
); |
if (array_key_exists($service, $tab)) { |
extract($tab[$service]); |
} else { |
if (strpos(Config::get('nom_projet'), 'bd') === 0 && $projet == null) { |
$projet = 'bdnt'; |
$service = 'ontologies'; |
$ressource = ''; |
} |
} |
$param = ($param) ? "?".$param : ""; |
$url = Config::get('url_service_base').$projet.'/'.$service.'/'.$ressource.$valeur.$param; |
return $url; |
} |
|
static function s_ajouterHrefAutreProjet($service, $ressource, $valeur, $projet = null, $param = null) { |
//on enleve les GA et Co, les meta ou les "_" |
self::s_transliterer($service, $valeur); |
//on définit les nom des projets, des services et des ressources de l'url (dans les méta-donnees) |
$tab = array( |
'langue' => array('service' => 'langues', 'projet' => 'iso-639-1', 'ressource' => ''), |
'couverture_spatiale' => array('service' => 'zone-geo', 'projet' => 'iso-3166-1', 'ressource' => ''), |
'type' => array('service' => 'ontologies', 'projet' => 'eflore', 'ressource' => 'contactType:'), |
'datum' => array('service' => 'ontologies', 'projet' => 'eflore', 'ressource' => 'datum:') |
); |
if (array_key_exists($service, $tab)) { |
extract($tab[$service]); |
} else { |
if (strpos(Config::get('nom_projet'), 'bd') === 0 && $projet == null) { |
$projet = 'bdnt'; |
$service = 'ontologies'; |
$ressource = ''; |
} |
} |
$param = ($param) ? "?".$param : ""; |
$url = Config::get('url_service_base').$projet.'/'.$service.'/'.$ressource.$valeur.$param; |
return $url; |
} |
|
/**Permet de consulter une url et retourne le résultat ou une erreur |
* @param $url */ |
public function consulterHref($url) { |
$res = $this->getRestClient()->consulter($url); |
$entete = $this->getRestClient()->getReponseEntetes(); |
//Si le service meta-donnees fonctionne correctement, l'entete comprend la clé wrapper_data |
if (isset($entete['wrapper_data'])) { |
$res = json_decode($res); |
return $res; |
} else { |
$u = 'L\'url <a href="'.$url.'">'.$url.'</a> lancée via RestClient renvoie une erreur'; |
$this->renvoyerErreur(RestServeur::HTTP_CODE_RESSOURCE_INTROUVABLE, $u); |
} |
} |
|
public function transliterer(&$service, &$val) { |
if (preg_match('/^.+:(.+)$/', $val, $match)) { |
$val = $match[1]; |
} |
$service = str_replace(array('_Ga','_Co','_meta'), '', $service); |
if ($service == 'rang') { |
$ressource = 'rangTaxo'; |
} elseif (preg_match('/^(statut)(?:_|-)([^_-]+)$/', $service, $match)) { |
$service = $match[1].ucfirst($match[2]); |
} elseif (strrpos($service, 'datum') !== false) { |
$service = 'datum'; |
} |
} |
|
static function s_transliterer(&$service, &$val) { |
if (preg_match('/^.+:(.+)$/', $val, $match)) { |
$val = $match[1]; |
} |
$service = str_replace(array('_Ga','_Co','_meta'), '', $service); |
if ($service == 'rang') { |
$ressource = 'rangTaxo'; |
} elseif (preg_match('/^(statut)(?:_|-)([^_-]+)$/', $service, $match)) { |
$service = $match[1].ucfirst($match[2]); |
} elseif (strrpos($service, 'datum') !== false) { |
$service = 'datum'; |
} |
} |
|
// prend en arguments la valeur de la recherche, les résultats approchés, le paramétre recherche |
// retourne le tableau trié en fonction de la ressemblance entre le résultat approché et la valeur recherchée |
public function trierRechercheFloue($nom_demande, $tab_approchee, $nom) { |
$trie = ''; |
$resultat = array(); |
foreach ($tab_approchee as $id => $tab) { |
$nom_demande_ss = strtolower(Chaine::supprimerAccents($nom_demande)); |
$nom_flou_ss = strtolower(Chaine::supprimerAccents($tab[$nom])); |
$stat = array(); |
// Prime pour la ressemblance globale : |
$score = 500 - levenshtein($nom_flou_ss, $nom_demande_ss); |
// On affine |
$score = $score + (similar_text($nom_demande_ss, $nom_flou_ss) * 3); |
$stat['score'] = $score; |
foreach ($tab as $key => $valeur) { |
$stat[$key] = $valeur; |
} |
$resultat[] = $stat; |
} |
|
|
// Vérification que nous avons bien trouvé un nom approché |
if (count($resultat) > 0) { |
$trie = Tableau::trierMD($resultat, array('score' => SORT_DESC)); |
} |
return $trie; |
} |
|
protected function recupererTableauConfig($param) { |
$tableau = array(); |
$tableauPartiel = explode(',', Config::get($param)); |
$tableauPartiel = array_map('trim', $tableauPartiel); |
foreach ($tableauPartiel as $champ) { |
if (strpos($champ, '=') === false) { |
$tableau[] = $champ; |
} else { |
list($cle, $val) = explode('=', $champ); |
$tableau[$cle] = $val; |
} |
} |
return $tableau; |
} |
|
static function s_recupererTableauConfig($param) { |
$tableau = array(); |
$tableauPartiel = array_map('trim', explode(',', Config::get($param))); |
foreach ($tableauPartiel as $champ) { |
if (strpos($champ, '=') === false) { |
$tableau[] = $champ; |
} else { |
list($cle, $val) = explode('=', $champ); |
$tableau[$cle] = $val; |
} |
} |
return $tableau; |
} |
|
//+------------------------------------------------------------------------------------------------------+ |
// Méthodes d'accès aux objets du Framework |
/** |
* Méthode de connection à la base de données sur demande. |
* Tous les services web n'ont pas besoin de s'y connecter. |
*/ |
protected function getBdd() { |
if (! isset($this->Bdd)) { |
$this->Bdd = new Bdd(); |
} |
return $this->Bdd; |
} |
|
/** |
* Méthode permettant de faire appel à un client REST en fonction des besoins du service. |
*/ |
protected function getRestClient() { |
if (! isset($this->RestClient)) { |
$this->RestClient = new RestClient(); |
} |
return $this->RestClient; |
} |
|
|
/** |
* Génération de fichiers pour les cartes |
*/ |
static function convertirEnPNGAvecRsvg($idFichier, $chemin, $svg) { |
// test répertoire de cache |
if(!is_dir($chemin)) { |
mkdir($chemin, 0777, true); |
} |
if(!is_dir($chemin)) { |
error_log(__FILE__ . ": can't create cache {$chemin}"); |
return NULL; |
} |
|
// test présence du binaire de conversion (rsvg) |
/* |
// `which` no possible using safe-mode... |
$i = $s = NULL; |
exec('which rsvg-convert', $s, $i); |
if($i != 0) { |
error_log(__FILE__ . ": no rsvg-convert binary"); |
return NULL; |
} |
*/ |
// conversion svg => png |
// troncage du nom de fichier si celui-ci est trop long |
// (passé 255 caractères, le risque de collision est très faible) |
$cheminReduit = substr($chemin.$idFichier, 0, 240); |
|
$fichierPng = $cheminReduit.'.png'; |
$fichierSvg = $cheminReduit.'.svg'; |
|
|
file_put_contents($fichierSvg, $svg); |
$i = $s = NULL; |
$rsvg = exec("rsvg-convert $fichierSvg -d 75 -p 75 -o $fichierPng", $s, $i); |
if($i != 0) { |
error_log(__FILE__ . ": `rsvg-convert $fichierSvg -o $fichierPng` returned $i: " . implode(', ', $s)); |
return NULL; |
} |
|
self::indexerFichierPng($fichierPng); |
return file_get_contents($fichierPng); |
} |
|
static function indexerFichierPng($fichierPng) { |
$img = imagecreatefrompng($fichierPng); |
imagetruecolortopalette($img, false, 32); |
$blanc = imagecolorallocate($img, 255, 255, 255); |
imagefill($img, 0, 0, $blanc); |
imagepng($img, $fichierPng, 9, PNG_ALL_FILTERS); |
} |
|
//+------------------------------------------------------------------------------------------------------+ |
// Fonctions appelées par plusieurs web services |
public function obtenirNumNomTaxonsSuperieurs($referentiel, $nn_demande) { |
$nn_taxons_sup = array(); |
// TODO: ceci ramène trop de champs alors que l'on a besoin que du numéro nomenclatural |
// et il y a peut-être un meilleur moyen que ramener la hierarchie des taxons supérieurs |
// mais pour le moment ça marche et c'est assez rapide |
$url = $this->ajouterHrefAutreProjet('taxons', $nn_demande, '/relations/superieurs',$referentiel); |
$classification = $this->consulterHref($url); |
$classification = is_object($classification) ? get_object_vars($classification) : array(); |
|
if(isset($classification[$nn_demande])) { |
$classification_nn_demande = get_object_vars($classification[$nn_demande]); |
$tab_nn_demandes = array_keys($classification_nn_demande); |
$nn_taxons_sup = $tab_nn_demandes; |
} |
return $nn_taxons_sup; |
} |
|
|
static function extraireComplementsOntologies($ontologie) { |
if (!$ontologie['complements']) return $ontologie; |
$complements = explode(',', trim($ontologie['complements'])); |
foreach ($complements as $complement) { |
@list($cle, $val) = explode('=', trim($complement)); |
// TODO: dirty workaround. Les compléments aux ontologies utilisent |
// des séparateurs variables. |
// cf disabledtestSeparateurToutesOntologies() dans tests/0.1/eflore/EfloreOntologiesTest.php |
// ainsi nous testons $cle et $val |
if($cle && $val) $ontologie[trim($cle)] = trim($val); |
} |
return $ontologie; |
} |
} |
?> |
Property changes: |
Added: svn:executable |
+* |
\ No newline at end of property |