diff --git a/htdocs/core/ajax/ajaxdirtree.php b/htdocs/core/ajax/ajaxdirtree.php index 9e823ec2116..d50b8217984 100644 --- a/htdocs/core/ajax/ajaxdirtree.php +++ b/htdocs/core/ajax/ajaxdirtree.php @@ -33,13 +33,14 @@ if (! defined('NOREQUIREAJAX')) define('NOREQUIREAJAX','1'); $res=@include("../../main.inc.php"); include_once(DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php'); +include_once(DOL_DOCUMENT_ROOT.'/core/lib/functions2.lib.php'); include_once(DOL_DOCUMENT_ROOT.'/core/lib/treeview.lib.php'); include_once(DOL_DOCUMENT_ROOT.'/core/class/html.form.class.php'); include_once(DOL_DOCUMENT_ROOT."/ecm/class/ecmdirectory.class.php"); $openeddir = GETPOST('openeddir'); $modulepart= GETPOST('modulepart'); -$selecteddir = urldecode(GETPOST('dir')); // relative patch. We must keep the urldecode here because para comes from jqueyrFileTree that url encode it. +$selecteddir = jsUnEscape(GETPOST('dir')); // relative path. We must decode using same encoding function used by javascript: escape() if ($selecteddir != '/') $selecteddir = preg_replace('/\/$/','',$selecteddir); // We removed last '/' except if it is '/' $langs->load("ecm"); @@ -89,7 +90,6 @@ foreach($sqltree as $keycursor => $val) } } -//var_dump($sqltree); if( file_exists($fullpathselecteddir) ) { @@ -111,6 +111,7 @@ if( file_exists($fullpathselecteddir) ) // Try to find key into $sqltree $val=array(); + foreach($sqltree as $key => $tmpval) { //print "-- ".$val['fullrelativename']." vs ".(($selecteddir != '/'?$selecteddir.'/':'').$file).'
'; diff --git a/htdocs/core/lib/files.lib.php b/htdocs/core/lib/files.lib.php index 494070575db..9e5a404ec10 100644 --- a/htdocs/core/lib/files.lib.php +++ b/htdocs/core/lib/files.lib.php @@ -23,6 +23,17 @@ * \brief Library for file managing functions */ +/** + * Make a basename working with all page code (default PHP basenamed fails with cyrillic). + * We supose dir separator for input is '/'. + * + * @param string $pathfile String to find basename. + * @return string Basename of input + */ +function dol_basename($pathfile) +{ + return preg_replace('/^.*\/([^\/]+)$/','$1',rtrim($pathfile,'/')); +} /** * Scan a directory and return a list of files/directories. diff --git a/htdocs/core/lib/functions2.lib.php b/htdocs/core/lib/functions2.lib.php index d938d41e974..a0305ef3ed8 100644 --- a/htdocs/core/lib/functions2.lib.php +++ b/htdocs/core/lib/functions2.lib.php @@ -24,6 +24,45 @@ * This file contains all rare functions. */ +/** + * Same function than javascript unescape() function but in PHP. + * + * @param string $sourcetodecode String to decode + * @return + */ +function jsUnEscape($source) +{ + $decodedStr = ""; + $pos = 0; + $len = strlen ($source); + while ($pos < $len) { + $charAt = substr ($source, $pos, 1); + if ($charAt == '%') { + $pos++; + $charAt = substr ($source, $pos, 1); + if ($charAt == 'u') { + // we got a unicode character + $pos++; + $unicodeHexVal = substr ($source, $pos, 4); + $unicode = hexdec ($unicodeHexVal); + $entity = "&#". $unicode . ';'; + $decodedStr .= utf8_encode ($entity); + $pos += 4; + } + else { + // we have an escaped ascii character + $hexVal = substr ($source, $pos, 2); + $decodedStr .= chr (hexdec ($hexVal)); + $pos += 2; + } + } else { + $decodedStr .= $charAt; + $pos++; + } + } + return dol_html_entity_decode($decodedStr, ENT_COMPAT); +} + /** * Return list of modules directories diff --git a/htdocs/ecm/class/ecmdirectory.class.php b/htdocs/ecm/class/ecmdirectory.class.php index b41e49f3032..a4cd7a79e64 100644 --- a/htdocs/ecm/class/ecmdirectory.class.php +++ b/htdocs/ecm/class/ecmdirectory.class.php @@ -607,8 +607,8 @@ class EcmDirectory // extends CommonObject } /** - * Calcule les proprietes fullpath, fullrelativename, fulllabel d'un repertoire - * du tableau this->cats et de toutes ces enfants. + * Define properties fullpath, fullrelativename, fulllabel of a directory of array this->cats and all its childs. + * Separator between directories is always '/', whatever is OS. * * @param int $id_categ id_categ entry to update * @param int $protection Deep counter to avoid infinite loop diff --git a/htdocs/ecm/index.php b/htdocs/ecm/index.php index 94d6ffcc543..bdbb630bb7f 100644 --- a/htdocs/ecm/index.php +++ b/htdocs/ecm/index.php @@ -257,7 +257,8 @@ if ($action == 'refreshmanual') } } else - { + { + dol_syslog("Parent is root"); $fk_parent=0; // Parent is root } @@ -265,7 +266,7 @@ if ($action == 'refreshmanual') { $ecmdirtmp=new EcmDirectory($db); $ecmdirtmp->ref = 'NOTUSEDYET'; - $ecmdirtmp->label = basename($dirdesc['fullname']); + $ecmdirtmp->label = dol_basename($dirdesc['fullname']); $ecmdirtmp->description = ''; $ecmdirtmp->fk_parent = $fk_parent; @@ -284,6 +285,10 @@ if ($action == 'refreshmanual') //var_dump($sqltree); $adirwascreated=1; } + else + { + dol_syslog("Failed to create directory ".$ecmdirtmp->label, LOG_ERR); + } } else { $txt="Parent of ".$dirdesc['fullname']." not found"; @@ -559,7 +564,7 @@ if (empty($action) || $action == 'file_manager' || preg_match('/refresh/i',$acti function loadandshowpreview(filedirname,section) { - //alert('filename='+filename); + alert('filename='+filename); jQuery('#ecmfileview').empty(); url='?action=preview&module=ecm§ion='+section+'&file='+urlencode(filedirname); @@ -584,10 +589,12 @@ if (empty($action) || $action == 'file_manager' || preg_match('/refresh/i',$acti jQuery(document).ready( function() { jQuery('#filetree').fileTree({ root: '', + // Called if we click on a file (not a dir) script: '', folderEvent: 'click', multiFolder: false }, - function(file) { + // Called if we click on a file (not a dir) + function(file) { jQuery("#mesg").hide(); loadandshowpreview(file,0); } diff --git a/test/phpunit/AllTests.php b/test/phpunit/AllTests.php index 60ce9eaac39..99d54901b41 100644 --- a/test/phpunit/AllTests.php +++ b/test/phpunit/AllTests.php @@ -72,6 +72,8 @@ class AllTests $suite->addTestSuite('ImagesLibTest'); require_once dirname(__FILE__).'/FunctionsTest.php'; $suite->addTestSuite('FunctionsTest'); + require_once dirname(__FILE__).'/Functions2Test.php'; + $suite->addTestSuite('Functions2Test'); require_once dirname(__FILE__).'/SecurityTest.php'; $suite->addTestSuite('SecurityTest'); diff --git a/test/phpunit/FilesLibTest.php b/test/phpunit/FilesLibTest.php index fb919ab56b9..76e19726e26 100644 --- a/test/phpunit/FilesLibTest.php +++ b/test/phpunit/FilesLibTest.php @@ -114,6 +114,38 @@ class FilesLibTest extends PHPUnit_Framework_TestCase print __METHOD__."\n"; } + + /** + * testDolBasename + * + * @return int + */ + public function testDolBasename() + { + global $conf,$user,$langs,$db; + $conf=$this->savconf; + $user=$this->savuser; + $langs=$this->savlangs; + $db=$this->savdb; + + $result=dol_basename('adir/afile'); + print __METHOD__." result=".$result."\n"; + $this->assertEquals('afile',$result); + + $result=dol_basename('adir/afile/'); + print __METHOD__." result=".$result."\n"; + $this->assertEquals('afile',$result); + + $result=dol_basename('adir/νεο'); // With cyrillic data. Here basename fails to return correct value + print __METHOD__." result=".$result."\n"; + $this->assertEquals('νεο',$result); + + $result=dol_basename('adir/νεο/'); // With cyrillic data. Here basename fails to return correct value + print __METHOD__." result=".$result."\n"; + $this->assertEquals('νεο',$result); + } + + /** * testDolCountNbOfLine * diff --git a/test/phpunit/Functions2Test.php b/test/phpunit/Functions2Test.php new file mode 100755 index 00000000000..9a6cc1163f2 --- /dev/null +++ b/test/phpunit/Functions2Test.php @@ -0,0 +1,134 @@ + + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + * or see http://www.gnu.org/ + */ + +/** + * \file test/phpunit/FunctionsTest.php + * \ingroup test + * \brief PHPUnit test + * \remarks To run this script as CLI: phpunit filename.php + */ + +global $conf,$user,$langs,$db; +//define('TEST_DB_FORCE_TYPE','mysql'); // This is to force using mysql driver +require_once 'PHPUnit/Autoload.php'; +require_once dirname(__FILE__).'/../../htdocs/master.inc.php'; +require_once dirname(__FILE__).'/../../htdocs/core/lib/functions2.lib.php'; + +if (! defined('NOREQUIREUSER')) define('NOREQUIREUSER','1'); +if (! defined('NOREQUIREDB')) define('NOREQUIREDB','1'); +if (! defined('NOREQUIRESOC')) define('NOREQUIRESOC','1'); +if (! defined('NOREQUIRETRAN')) define('NOREQUIRETRAN','1'); +if (! defined('NOCSRFCHECK')) define('NOCSRFCHECK','1'); +if (! defined('NOTOKENRENEWAL')) define('NOTOKENRENEWAL','1'); +if (! defined('NOREQUIREMENU')) define('NOREQUIREMENU','1'); // If there is no menu to show +if (! defined('NOREQUIREHTML')) define('NOREQUIREHTML','1'); // If we don't need to load the html.form.class.php +if (! defined('NOREQUIREAJAX')) define('NOREQUIREAJAX','1'); +if (! defined("NOLOGIN")) define("NOLOGIN",'1'); // If this page is public (can be called outside logged session) + + +/** + * Class for PHPUnit tests + * + * @backupGlobals disabled + * @backupStaticAttributes enabled + * @remarks backupGlobals must be disabled to have db,conf,user and lang not erased. + */ +class Functions2Test extends PHPUnit_Framework_TestCase +{ + protected $savconf; + protected $savuser; + protected $savlangs; + protected $savdb; + + /** + * Constructor + * We save global variables into local variables + * + * @return CoreTest + */ + function Functions2Test() + { + //$this->sharedFixture + global $conf,$user,$langs,$db; + $this->savconf=$conf; + $this->savuser=$user; + $this->savlangs=$langs; + $this->savdb=$db; + + print __METHOD__." db->type=".$db->type." user->id=".$user->id; + //print " - db ".$db->db; + print "\n"; + } + + // Static methods + public static function setUpBeforeClass() + { + global $conf,$user,$langs,$db; + //$db->begin(); // This is to have all actions inside a transaction even if test launched without suite. + + print __METHOD__."\n"; + } + public static function tearDownAfterClass() + { + global $conf,$user,$langs,$db; + //$db->rollback(); + + print __METHOD__."\n"; + } + + /** + * Init phpunit tests + * + * @return void + */ + protected function setUp() + { + global $conf,$user,$langs,$db; + $conf=$this->savconf; + $user=$this->savuser; + $langs=$this->savlangs; + $db=$this->savdb; + + print __METHOD__."\n"; + } + /** + * End phpunit tests + * + * @return void + */ + protected function tearDown() + { + print __METHOD__."\n"; + } + + + /** + * testJsUnEscape + * + * @return void + */ + public function testJsUnEscape() + { + $result=jsUnEscape('%u03BD%u03B5%u03BF'); + print __METHOD__." result=".$result."\n"; + $this->assertEquals('νεο',$result); + + return; + } +} +?> \ No newline at end of file