diff --git a/htdocs/core/class/commonobject.class.php b/htdocs/core/class/commonobject.class.php index 3ad080d8a55..3287ac5d4b7 100644 --- a/htdocs/core/class/commonobject.class.php +++ b/htdocs/core/class/commonobject.class.php @@ -3987,7 +3987,7 @@ abstract class CommonObject function call_trigger($trigger_name, $user) { global $langs,$conf; - + include_once DOL_DOCUMENT_ROOT . '/core/class/interfaces.class.php'; $interface=new Interfaces($this->db); $result=$interface->run_triggers($trigger_name,$this,$user,$langs,$conf); diff --git a/htdocs/core/class/interfaces.class.php b/htdocs/core/class/interfaces.class.php index 7b233a4fff8..1ac219029fd 100644 --- a/htdocs/core/class/interfaces.class.php +++ b/htdocs/core/class/interfaces.class.php @@ -77,7 +77,7 @@ class Interfaces $modules = array(); $orders = array(); $i=0; - + $dirtriggers=array_merge(array('/core/triggers'),$conf->modules_parts['triggers']); foreach($dirtriggers as $reldir) { @@ -100,9 +100,9 @@ class Interfaces $part3=$reg[3]; $nbfile++; - + $modName = "Interface".ucfirst($reg[3]); - //print "file=$file"; print "modName=$modName"; exit; + //print "file=$file - modName=$modName\n"; if (in_array($modName,$modules)) { $langs->load("errors"); @@ -111,9 +111,17 @@ class Interfaces } else { - include_once $newdir.'/'.$file; + try { + //print 'Todo for '.$modName." : ".$newdir.'/'.$file."\n"; + include_once $newdir.'/'.$file; + //print 'Done for '.$modName."\n"; + } + catch(Exception $e) + { + dol_syslog('ko for '.$modName." ".$e->getMessage()."\n", LOG_ERROR); + } } - + // Check if trigger file is disabled by name if (preg_match('/NORUN$/i',$file)) continue; // Check if trigger file is for a particular module @@ -142,7 +150,7 @@ class Interfaces } asort($orders); - + // Loop on each trigger foreach ($orders as $key => $value) { diff --git a/htdocs/user/class/api_user.class.php b/htdocs/user/class/api_user.class.php index af0db5bfb2d..e89a5faac0b 100644 --- a/htdocs/user/class/api_user.class.php +++ b/htdocs/user/class/api_user.class.php @@ -96,36 +96,74 @@ class UserApi extends DolibarrApi function createFromContact($contactid, $request_data = NULL) { //if (!DolibarrApiAccess::$user->rights->user->user->creer) { //throw new RestException(401); - //} + //} + + if (!isset($request_data["login"])) + throw new RestException(400, "login field missing"); + if (!isset($request_data["password"])) + throw new RestException(400, "password field missing"); + if (!DolibarrApiAccess::$user->rights->societe->contact->lire) { + throw new RestException(401); + } + $contact = new Contact($this->db); + $contact->fetch($contactid); + if ($contact->id <= 0) { + throw new RestException(404, 'Contact not found'); + } - if (!isset($request_data["login"])) - throw new RestException(400, "login field missing"); - if (!isset($request_data["password"])) - throw new RestException(400, "password field missing"); - if (!DolibarrApiAccess::$user->rights->societe->contact->lire) { - throw new RestException(401); - } - $contact = new Contact($this->db); - $contact->fetch($contactid); - if ($contact->id <= 0) { - throw new RestException(404, 'Contact not found'); - } - - if (!DolibarrApi::_checkAccessToResource('contact', $contact->id, 'socpeople&societe')) { - throw new RestException(401, 'Access not allowed for login ' . DolibarrApiAccess::$user->login); - } - // Check mandatory fields - $login = $request_data["login"]; - $password = $request_data["password"]; - $result = $this->useraccount->create_from_contact($contact,$login,$password); - if ($result <= 0) { - throw new RestException(500, "User not created"); - } - // password parameter not used in create_from_contact - $this->useraccount->setPassword($this->useraccount,$password); - return $result; + if (!DolibarrApi::_checkAccessToResource('contact', $contact->id, 'socpeople&societe')) { + throw new RestException(401, 'Access not allowed for login ' . DolibarrApiAccess::$user->login); + } + // Check mandatory fields + $login = $request_data["login"]; + $password = $request_data["password"]; + $result = $this->useraccount->create_from_contact($contact,$login,$password); + if ($result <= 0) { + throw new RestException(500, "User not created"); + } + // password parameter not used in create_from_contact + $this->useraccount->setPassword($this->useraccount,$password); + + return $result; } - + + + /** + * Create user account + * + * @param array $request_data New user data + * @return int + * + * @url POST user/ + */ + function post($request_data = NULL) { + // check user authorization + //if(! DolibarrApiAccess::$user->rights->user->creer) { + // throw new RestException(401, "User creation not allowed"); + //} + // check mandatory fields + /*if (!isset($request_data["login"])) + throw new RestException(400, "login field missing"); + if (!isset($request_data["password"])) + throw new RestException(400, "password field missing"); + if (!isset($request_data["lastname"])) + throw new RestException(400, "lastname field missing");*/ + //assign field values + $xxx=var_export($request_data, true); + dol_syslog("xxx=".$xxx); + foreach ($request_data as $field => $value) + { + $this->useraccount->$field = $value; + } + + $result = $this->useraccount->create(DolibarrApiAccess::$user); + if ($result <=0) { + throw new RestException(500, "User not created : ".$this->useraccount->error); + } + return array('id'=>$result); + } + + /** * Update account * @@ -159,10 +197,10 @@ class UserApi extends DolibarrApi if ($this->useraccount->update($id, DolibarrApiAccess::$user, 1, '', '', 'update')) return $this->get($id); - return false; - } + return false; + } - /** + /** * add user to group * * @param int $id User ID @@ -175,20 +213,20 @@ class UserApi extends DolibarrApi //if (!DolibarrApiAccess::$user->rights->user->user->supprimer) { //throw new RestException(401); //} - $result = $this->useraccount->fetch($id); - if (!$result) - { - throw new RestException(404, 'User not found'); + $result = $this->useraccount->fetch($id); + if (!$result) + { + throw new RestException(404, 'User not found'); + } + + if (!DolibarrApi::_checkAccessToResource('user', $this->useraccount->id, 'user')) + { + throw new RestException(401, 'Access not allowed for login ' . DolibarrApiAccess::$user->login); + } + + return $this->useraccount->SetInGroup($group,1); } - if (!DolibarrApi::_checkAccessToResource('user', $this->useraccount->id, 'user')) - { - throw new RestException(401, 'Access not allowed for login ' . DolibarrApiAccess::$user->login); - } - - return $this->useraccount->SetInGroup($group,1); - } - /** * Delete account * diff --git a/test/phpunit/AllTests.php b/test/phpunit/AllTests.php index 8dd9941d8b4..2dfdf4cb5c2 100644 --- a/test/phpunit/AllTests.php +++ b/test/phpunit/AllTests.php @@ -184,6 +184,9 @@ class AllTests require_once dirname(__FILE__).'/CategorieTest.php'; $suite->addTestSuite('CategorieTest'); + require_once dirname(__FILE__).'/RestAPIUserTest.php'; + $suite->addTestSuite('RestAPIUserTest'); + require_once dirname(__FILE__).'/WebservicesProductsTest.php'; $suite->addTestSuite('WebservicesProductsTest'); require_once dirname(__FILE__).'/WebservicesInvoicesTest.php'; diff --git a/test/phpunit/RestAPIUserTest.php b/test/phpunit/RestAPIUserTest.php new file mode 100644 index 00000000000..466c3cab782 --- /dev/null +++ b/test/phpunit/RestAPIUserTest.php @@ -0,0 +1,225 @@ + + * + * 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 3 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/RestAPIUserTest.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/date.lib.php'; +require_once dirname(__FILE__).'/../../htdocs/core/lib/geturl.lib.php'; + + +if (empty($user->id)) { + print "Load permissions for admin user nb 1\n"; + $user->fetch(1); + $user->getrights(); +} +$conf->global->MAIN_DISABLE_ALL_MAILS=1; +$conf->global->MAIN_UMASK='0666'; + + +/** + * Class for PHPUnit tests + * + * @backupGlobals disabled + * @backupStaticAttributes enabled + * @remarks backupGlobals must be disabled to have db,conf,user and lang not erased. + */ +class RestAPIUserTest extends PHPUnit_Framework_TestCase +{ + protected $savconf; + protected $savuser; + protected $savlangs; + protected $savdb; + protected $api_url; + protected $api_key; + + /** + * Constructor + * We save global variables into local variables + * + * @return DateLibTest + */ + function __construct() + { + //$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"; + } + + // tear down after class + 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; + + $this->api_url=DOL_MAIN_URL_ROOT.'/api/index.php'; + + $login='admin'; + $password='admin'; + $url=$this->api_url.'/login?login='.$login.'&password='.$password; + // Call the API login method to save api_key for this test class + $result=getURLContent($url, 'GET', '', 1, array()); + //print __METHOD__." result = ".var_export($result, true)."\n"; + print __METHOD__." curl_error_no: ".$result['curl_error_no']."\n"; + $this->assertEquals($result['curl_error_no'],''); + $object=json_decode($result['content'], true); + $this->assertNotNull($object, "Parsing of json result must no be null"); + $this->assertEquals('200', $object['success']['code']); + + $this->api_key = $object['success']['token']; + print __METHOD__." api_key: $this->api_key \n"; + + print __METHOD__."\n"; + } + + /** + * End phpunit tests + * + * @return void + */ + protected function tearDown() + { + print __METHOD__."\n"; + } + + + /** + * testRestGetUser + * + * @return int + */ + public function testRestGetUser() + { + global $conf,$user,$langs,$db; + + $url = $this->api_url.'/user/123456789?api_key='.$this->api_key; + //$addheaders=array('Content-Type: application/json'); + + print __METHOD__." Request url=".$url."\n"; + $result=getURLContent($url, 'GET', '', 1, array()); + //print __METHOD__." Result for unexisting user: ".var_export($result, true)."\n"; + print __METHOD__." curl_error_no: ".$result['curl_error_no']."\n"; + $this->assertEquals($result['curl_error_no'],''); + $object=json_decode($result['content'], true); + $this->assertNotNull($object, "Parsing of json result must no be null"); + $this->assertEquals(404, $object['error']['code']); + + $url = $this->api_url.'/user/1?api_key='.$this->api_key; + + print __METHOD__." Request url=".$url."\n"; + $result=getURLContent($url, 'GET', '', 1, array()); + //print __METHOD__." Result for existing user user: ".var_export($result, true)."\n"; + print __METHOD__." curl_error_no: ".$result['curl_error_no']."\n"; + $this->assertEquals($result['curl_error_no'],''); + $object=json_decode($result['content'], true); + $this->assertNotNull($object, "Parsing of json result must no be null"); + $this->assertEquals(1, $object['statut']); + } + + public function testRestCreateUser() { + + // attemp to create without mandatory fields : + $url = $this->api_url.'/user?api_key='.$this->api_key; + $addheaders=array('Content-Type: application/json'); + + $bodyobj = array( + "lastname"=>"testRestUser", + "password"=>"testRestPassword", + "email"=>"test@restuser.com" + ); + $body = json_encode($bodyobj); + + print __METHOD__." Request url=".$url."\n"; + $result=getURLContent($url, 'POST', $body, 1, $addheaders); + //print __METHOD__." Result for creating incomplete user".var_export($result, true)."\n"; + print __METHOD__." curl_error_no: ".$result['curl_error_no']."\n"; + $this->assertEquals($result['curl_error_no'],''); + $object=json_decode($result['content'], true); + $this->assertNotNull($object, "Parsing of json result must no be null"); + $this->assertEquals(500, $object['error']['code'], $object['error']['code'].' '.$object['error']['message']); + + // create regular user + unset($result); + $bodyobj = array( + "login"=>"testRestLogin".mt_rand(), + "lastname"=>"testRestUser", + "password"=>"testRestPassword", + "email"=>"test@restuser.com" + ); + $body = json_encode($bodyobj); + print __METHOD__." Request url=".$url."\n"; + $result=getURLContent($url, 'POST', $body, 1, $addheaders); + print __METHOD__." Result code for creating user ".var_export($result, true)."\n"; + print __METHOD__." curl_error_no: ".$result['curl_error_no']."\n"; + $this->assertEquals($result['curl_error_no'],''); + $object=json_decode($result['content'], true); + $this->assertNotNull($object, "Parsing of json result must no be null"); + $this->assertGreaterThan(0, $object['id'], $object['error']['code'].' '.$object['error']['message']); + + // attempt to create duplicated user + print __METHOD__." Request url=".$url."\n"; + $result=getURLContent($url, 'POST', $body, 1, $addheaders); + //print __METHOD__." Result for creating duplicate user".var_export($result, true)."\n"; + print __METHOD__." curl_error_no: ".$result['curl_error_no']."\n"; + $this->assertEquals($result['curl_error_no'],''); + $object=json_decode($result['content'], true); + $this->assertNotNull($object, "Parsing of json result must no be null"); + $this->assertEquals(500, $object['error']['code'], $object['error']['code'].' '.$object['error']['message']); + } + +} \ No newline at end of file