Add unique key. Dolibarrize view of stripe card.

This commit is contained in:
Laurent Destailleur
2018-03-13 17:32:49 +01:00
parent a955e74329
commit 944ba69cd8
7 changed files with 158 additions and 75 deletions

View File

@@ -81,9 +81,10 @@ class Form
* @param string $moreparam More param to add on a href URL.
* @param int $fieldrequired 1 if we want to show field as mandatory using the "fieldrequired" CSS.
* @param int $notabletag 1=Do not output table tags but output a ':', 2=Do not output table tags and no ':', 3=Do not output table tags but output a ' '
* @param string $paramid Key of parameter for id ('id', 'socid')
* @return string HTML edit field
*/
function editfieldkey($text, $htmlname, $preselected, $object, $perm, $typeofdata='string', $moreparam='', $fieldrequired=0, $notabletag=0)
function editfieldkey($text, $htmlname, $preselected, $object, $perm, $typeofdata='string', $moreparam='', $fieldrequired=0, $notabletag=0, $paramid='id')
{
global $conf,$langs;
@@ -117,7 +118,7 @@ class Form
if (! empty($notabletag)) $ret.=' ';
if (empty($notabletag) && GETPOST('action','aZ09') != 'edit'.$htmlname && $perm) $ret.='</td>';
if (empty($notabletag) && GETPOST('action','aZ09') != 'edit'.$htmlname && $perm) $ret.='<td align="right">';
if ($htmlname && GETPOST('action','aZ09') != 'edit'.$htmlname && $perm) $ret.='<a href="'.$_SERVER["PHP_SELF"].'?action=edit'.$htmlname.'&amp;id='.$object->id.$moreparam.'">'.img_edit($langs->trans('Edit'), ($notabletag ? 0 : 1)).'</a>';
if ($htmlname && GETPOST('action','aZ09') != 'edit'.$htmlname && $perm) $ret.='<a href="'.$_SERVER["PHP_SELF"].'?action=edit'.$htmlname.'&amp;'.$paramid.'='.$object->id.$moreparam.'">'.img_edit($langs->trans('Edit'), ($notabletag ? 0 : 1)).'</a>';
if (! empty($notabletag) && $notabletag == 1) $ret.=' : ';
if (! empty($notabletag) && $notabletag == 3) $ret.=' ';
if (empty($notabletag) && GETPOST('action','aZ09') != 'edit'.$htmlname && $perm) $ret.='</td>';
@@ -142,9 +143,10 @@ class Form
* @param string $moreparam More param to add on a href URL
* @param int $notabletag Do no output table tags
* @param string $formatfunc Call a specific function to output field
* @param string $paramid Key of parameter for id ('id', 'socid')
* @return string HTML edit field
*/
function editfieldval($text, $htmlname, $value, $object, $perm, $typeofdata='string', $editvalue='', $extObject=null, $custommsg=null, $moreparam='', $notabletag=0, $formatfunc='')
function editfieldval($text, $htmlname, $value, $object, $perm, $typeofdata='string', $editvalue='', $extObject=null, $custommsg=null, $moreparam='', $notabletag=0, $formatfunc='', $paramid='id')
{
global $conf,$langs,$db;
@@ -166,7 +168,7 @@ class Form
$ret.='<form method="post" action="'.$_SERVER["PHP_SELF"].($moreparam?'?'.$moreparam:'').'">';
$ret.='<input type="hidden" name="action" value="set'.$htmlname.'">';
$ret.='<input type="hidden" name="token" value="'.$_SESSION['newtoken'].'">';
$ret.='<input type="hidden" name="id" value="'.$object->id.'">';
$ret.='<input type="hidden" name="'.$paramid.'" value="'.$object->id.'">';
if (empty($notabletag)) $ret.='<table class="nobordernopadding" cellpadding="0" cellspacing="0">';
if (empty($notabletag)) $ret.='<tr><td>';
if (preg_match('/^(string|email)/',$typeofdata))

View File

@@ -208,6 +208,9 @@ function societe_prepare_head(Societe $object)
else {
dol_print_error($db);
}
//if (! empty($conf->stripe->enabled) && $nbBankAccount > 0) $nbBankAccount = '...'; // No way to know exact number
if ($nbBankAccount > 0) $head[$h][1].= ' <span class="badge">'.$nbBankAccount.'</span>';
$head[$h][2] = 'rib';
$h++;

View File

@@ -260,7 +260,7 @@ CREATE TABLE llx_societe_account(
entity integer DEFAULT 1,
key_account varchar(128),
login varchar(128) NOT NULL,
pass_encoding varchar(24) NOT NULL,
pass_encoding varchar(24),
pass_crypted varchar(128),
pass_temp varchar(128), -- temporary password when asked for forget password
fk_soc integer,
@@ -278,6 +278,7 @@ CREATE TABLE llx_societe_account(
-- END MODULEBUILDER FIELDS
) ENGINE=innodb;
-- VMYSQL4.3 ALTER TABLE llx_societe_account MODIFY COLUMN pass_encoding varchar(24) NULL;
ALTER TABLE llx_societe_account ADD COLUMN key_account varchar(128);
@@ -288,6 +289,7 @@ ALTER TABLE llx_societe_account ADD INDEX idx_societe_account_fk_website (fk_web
ALTER TABLE llx_societe_account ADD INDEX idx_societe_account_fk_soc (fk_soc);
ALTER TABLE llx_societe_account ADD UNIQUE INDEX uk_societe_account_login_website_soc(entity, fk_soc, login, site, fk_website);
ALTER TABLE llx_societe_account ADD UNIQUE INDEX uk_societe_account_key_account_soc(entity, fk_soc, key_account, site, fk_website);
ALTER TABLE llx_societe_account ADD CONSTRAINT llx_societe_account_fk_website FOREIGN KEY (fk_website) REFERENCES llx_website(rowid);
ALTER TABLE llx_societe_account ADD CONSTRAINT llx_societe_account_fk_societe FOREIGN KEY (fk_soc) REFERENCES llx_societe(rowid);

View File

@@ -23,6 +23,7 @@ ALTER TABLE llx_societe_account ADD INDEX idx_societe_account_fk_soc (fk_soc);
-- END MODULEBUILDER INDEXES
ALTER TABLE llx_societe_account ADD UNIQUE INDEX uk_societe_account_login_website_soc(entity, fk_soc, login, site, fk_website);
ALTER TABLE llx_societe_account ADD UNIQUE INDEX uk_societe_account_key_account_soc(entity, fk_soc, key_account, site, fk_website);
ALTER TABLE llx_societe_account ADD CONSTRAINT llx_societe_account_fk_website FOREIGN KEY (fk_website) REFERENCES llx_website(rowid);
ALTER TABLE llx_societe_account ADD CONSTRAINT llx_societe_account_fk_societe FOREIGN KEY (fk_soc) REFERENCES llx_societe(rowid);

View File

@@ -21,7 +21,7 @@ CREATE TABLE llx_societe_account(
entity integer DEFAULT 1,
key_account varchar(128),
login varchar(128) NOT NULL,
pass_encoding varchar(24) NOT NULL,
pass_encoding varchar(24),
pass_crypted varchar(128),
pass_temp varchar(128), -- temporary password when asked for forget password
fk_soc integer,

View File

@@ -20,9 +20,9 @@
*/
/**
* \file class/websiteaccount.class.php
* \ingroup website
* \brief This file is a CRUD class file for WebsiteAccount (Create/Read/Update/Delete)
* \file class/societeaccount.class.php
* \ingroup societe
* \brief This file is a CRUD class file for SocieteAccount (Create/Read/Update/Delete)
*/
// Put here all includes required by your class file
@@ -31,24 +31,24 @@ require_once DOL_DOCUMENT_ROOT . '/core/class/commonobject.class.php';
//require_once DOL_DOCUMENT_ROOT . '/product/class/product.class.php';
/**
* Class for WebsiteAccount
* Class for SocieteAccount
*/
class WebsiteAccount extends CommonObject
class SocieteAccount extends CommonObject
{
/**
* @var string ID to identify managed object
*/
public $element = 'websiteaccount';
public $element = 'societeaccount';
/**
* @var string Name of table without prefix where object is stored
*/
public $table_element = 'website_account';
public $table_element = 'societe_account';
/**
* @var array Does websiteaccount support multicompany module ? 0=No test on entity, 1=Test with field entity, 2=Test with link by societe
* @var array Does societeaccount support multicompany module ? 0=No test on entity, 1=Test with field entity, 2=Test with link by societe
*/
public $ismultientitymanaged = 0;
/**
* @var string String with name of icon for websiteaccount. Must be the part after the 'object_' into object_myobject.png
* @var string String with name of icon for societeaccount. Must be the part after the 'object_' into object_myobject.png
*/
public $picto = 'lock';
@@ -76,12 +76,15 @@ class WebsiteAccount extends CommonObject
*/
public $fields=array(
'rowid' => array('type'=>'integer', 'label'=>'TechnicalID', 'visible'=>-2, 'enabled'=>1, 'position'=>1, 'notnull'=>1, 'index'=>1, 'comment'=>'Id',),
'login' => array('type'=>'varchar(64)', 'label'=>'Login', 'visible'=>1, 'enabled'=>1, 'position'=>10, 'notnull'=>1, 'index'=>1, 'searchall'=>1, 'comment'=>'Login',),
'entity' => array('type'=>'integer', 'label'=>'Entity', 'visible'=>0, 'enabled'=>1, 'position'=>5, 'default'=>1),
'key_account' => array('type'=>'varchar(128)', 'label'=>'KeyAccount', 'visible'=>-1, 'enabled'=>1, 'position'=>10, 'notnull'=>1, 'index'=>1, 'searchall'=>1, 'comment'=>'Key account',),
'login' => array('type'=>'varchar(64)', 'label'=>'Login', 'visible'=>1, 'enabled'=>1, 'position'=>10),
'pass_encoding' => array('type'=>'varchar(24)', 'label'=>'PassEncoding', 'visible'=>0, 'enabled'=>1, 'position'=>30),
'pass_crypted' => array('type'=>'varchar(128)', 'label'=>'Password', 'visible'=>1, 'enabled'=>1, 'position'=>31, 'notnull'=>1),
'pass_temp' => array('type'=>'varchar(128)', 'label'=>'Temp', 'visible'=>0, 'enabled'=>0, 'position'=>32, 'notnull'=>-1,),
'fk_soc' => array('type'=>'integer:Societe:societe/class/societe.class.php', 'label'=>'ThirdParty', 'visible'=>1, 'enabled'=>1, 'position'=>40, 'notnull'=>-1, 'index'=>1),
'fk_website' => array('type'=>'integer:Website:website/class/website.class.php', 'label'=>'WebSite', 'visible'=>1, 'enabled'=>1, 'position'=>41, 'notnull'=>1, 'index'=>1),
'site' => array('type'=>'varchar(128)', 'label'=>'Site', 'visible'=>-1, 'enabled'=>1, 'position'=>41),
'fk_website' => array('type'=>'integer:Website:website/class/website.class.php', 'label'=>'WebSite', 'visible'=>1, 'enabled'=>1, 'position'=>42, 'notnull'=>1, 'index'=>1),
'date_last_login' => array('type'=>'datetime', 'label'=>'LastConnexion', 'visible'=>2, 'enabled'=>1, 'position'=>50, 'notnull'=>0,),
'date_previous_login' => array('type'=>'datetime', 'label'=>'PreviousConnexion', 'visible'=>2, 'enabled'=>1, 'position'=>51, 'notnull'=>0,),
//'note_public' => array('type'=>'text', 'label'=>'NotePublic', 'visible'=>-1, 'enabled'=>1, 'position'=>45, 'notnull'=>-1,),
@@ -94,9 +97,13 @@ class WebsiteAccount extends CommonObject
'status' => array('type'=>'integer', 'label'=>'Status', 'visible'=>1, 'enabled'=>1, 'position'=>1000, 'notnull'=>1, 'index'=>1, 'default'=>1, 'arrayofkeyval'=>array('1'=>'Active','0'=>'Disabled')),
);
public $rowid;
public $login;
public $entity;
public $key_account;
public $pass_encoding;
public $pass_crypted;
public $pass_temp;
public $fk_soc;
public $site;
public $date_last_login;
public $date_previous_login;
public $note_private;
@@ -106,7 +113,6 @@ class WebsiteAccount extends CommonObject
public $fk_user_modif;
public $import_key;
public $status;
public $fk_soc;
// END MODULEBUILDER PROPERTIES
@@ -117,21 +123,21 @@ class WebsiteAccount extends CommonObject
/**
* @var int Name of subtable line
*/
//public $table_element_line = 'website_accountdet';
//public $table_element_line = 'societe_accountdet';
/**
* @var int Field with ID of parent key if this field has a parent
*/
//public $fk_element = 'fk_website_account';
//public $fk_element = 'fk_societe_account';
/**
* @var int Name of subtable class that manage subtable lines
*/
//public $class_element_line = 'WebsiteAccountline';
//public $class_element_line = 'societeAccountline';
/**
* @var array Array of child tables (child tables to delete before deleting a record)
*/
//protected $childtables=array('website_accountdet');
//protected $childtables=array('societe_accountdet');
/**
* @var WebsiteAccountLine[] Array of subtable lines
* @var societeAccountLine[] Array of subtable lines
*/
//public $lines = array();
@@ -235,7 +241,7 @@ class WebsiteAccount extends CommonObject
{
$this->lines=array();
// Load lines with object WebsiteAccountLine
// Load lines with object societeAccountLine
return count($this->lines)?1:0;
}
@@ -287,12 +293,12 @@ class WebsiteAccount extends CommonObject
$this->ref = $this->login;
$label = '<u>' . $langs->trans("WebsiteAccount") . '</u>';
$label = '<u>' . $langs->trans("SocieteAccount") . '</u>';
$label.= '<br>';
$label.= '<b>' . $langs->trans('Login') . ':</b> ' . $this->ref;
//$label.= '<b>' . $langs->trans('WebSite') . ':</b> ' . $this->ref;
$url = dol_buildpath('/website/websiteaccount_card.php',1).'?id='.$this->id;
$url = dol_buildpath('/societe/societeaccount_card.php',1).'?id='.$this->id;
if ($option != 'nolink')
{
@@ -307,7 +313,7 @@ class WebsiteAccount extends CommonObject
{
if (! empty($conf->global->MAIN_OPTIMIZEFORTEXTBROWSER))
{
$label=$langs->trans("ShowWebsiteAccount");
$label=$langs->trans("ShowsocieteAccount");
$linkclose.=' alt="'.dol_escape_htmltag($label, 1).'"';
}
$linkclose.=' title="'.dol_escape_htmltag($label, 1).'"';
@@ -486,10 +492,10 @@ class WebsiteAccount extends CommonObject
}
/**
* Class WebsiteAccountLine. You can also remove this and generate a CRUD class for lines objects.
* Class societeAccountLine. You can also remove this and generate a CRUD class for lines objects.
*/
/*
class WebsiteAccountLine
class societeAccountLine
{
// @var int ID
public $id;

View File

@@ -33,13 +33,11 @@ require_once DOL_DOCUMENT_ROOT.'/core/lib/company.lib.php';
require_once DOL_DOCUMENT_ROOT.'/core/lib/bank.lib.php';
require_once DOL_DOCUMENT_ROOT.'/core/class/html.formfile.class.php';
require_once DOL_DOCUMENT_ROOT.'/societe/class/companybankaccount.class.php';
require_once DOL_DOCUMENT_ROOT.'/societe/class/societeaccount.class.php';
require_once DOL_DOCUMENT_ROOT.'/compta/prelevement/class/bonprelevement.class.php';
require_once DOL_DOCUMENT_ROOT.'/stripe/class/stripe.class.php';
$langs->load("companies");
$langs->load("commercial");
$langs->load("banks");
$langs->load("bills");
$langs->loadLangs(array("companies","commercial","banks","bills"));
// Security check
$socid = GETPOST("socid","int");
@@ -50,6 +48,7 @@ $id=GETPOST("id","int");
$source=GETPOST("source","alpha");
$ribid=GETPOST("ribid","int");
$action=GETPOST("action", 'alpha', 3);
$cancel=GETPOST('cancel', 'alpha');
$object = new Societe($db);
$object->fetch($socid);
@@ -90,6 +89,11 @@ if (! empty($conf->stripe->enabled))
* Actions
*/
if ($cancel)
{
$action='';
}
$parameters=array('id'=>$socid, 'objcanvas'=>$objcanvas);
$reshook=$hookmanager->executeHooks('doActions',$parameters,$object,$action); // Note that $action and $object may have been modified by some hooks
if ($reshook < 0) setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
@@ -344,35 +348,88 @@ if (empty($reshook))
include DOL_DOCUMENT_ROOT.'/core/actions_builddoc.inc.php';
$id = $savid;
}
// Action for stripe
if (! empty($conf->stripe->enabled) && class_exists('Stripe'))
{
if ($action == 'setassourcedefault')
// Action for stripe
if (! empty($conf->stripe->enabled) && class_exists('Stripe'))
{
$cu = \Stripe\Customer::retrieve($stripecu);
if ($action == 'setkey_account')
{
$error = 0;
$cu->default_source = "$source"; // obtained with Stripe.js
$cu->save();
$newcu = GETPOST('key_account', 'alpha');
$url=DOL_URL_ROOT.'/societe/paymentmodes.php?socid='.$object->id;
header('Location: '.$url);
exit;
}
elseif ($action == 'delete')
{
$cu = \Stripe\Customer::retrieve($stripecu);
$db->begin();
$cu->sources->retrieve("$source")->detach();
$sql = 'UPDATE '.MAIN_DB_PREFIX."societe_account";
$sql.= " SET key_account = '".$db->escape(GETPOST('key_account', 'alpha'))."'";
$sql.= " WHERE site = 'stripe' AND fk_soc = ".$object->id." AND status = ".$servicestatus." AND entity = ".$conf->entity; // Keep = here for entity. Only 1 record must be modified !
$url=DOL_URL_ROOT.'/societe/paymentmodes.php?socid='.$object->id;
header('Location: '.$url);
exit;
$resql = $db->query($sql);
$num = $db->num_rows($resql);
if (empty($num))
{
$societeaccount = new SocieteAccount($db);
$societeaccount->fk_soc = $object->id;
$societeaccount->login = '';
$societeaccount->pass_encoding = '';
$societeaccount->site = 'stripe';
$societeaccount->status = $servicestatus;
$societeaccount->key_account = $newcu;
$result = $societeaccount->create($user);
if ($result < 0)
{
$error++;
}
}
if (! $error)
{
$stripecu = $newcu;
$db->commit();
}
else
{
$db->rollback();
}
}
if ($action == 'setassourcedefault')
{
try {
$cu = \Stripe\Customer::retrieve($stripecu);
$cu->default_source = (string) $source;
$result = $cu->save();
$url=DOL_URL_ROOT.'/societe/paymentmodes.php?socid='.$object->id;
header('Location: '.$url);
exit;
}
catch(Exception $e)
{
}
}
elseif ($action == 'delete')
{
try {
$cu = \Stripe\Customer::retrieve($stripecu);
$cu->sources->retrieve("$source")->detach();
$url=DOL_URL_ROOT.'/societe/paymentmodes.php?socid='.$object->id;
header('Location: '.$url);
exit;
}
catch(Exception $e)
{
}
}
}
}
/*
* View
*/
@@ -459,13 +516,15 @@ if ($socid && $action != 'edit' && $action != "create")
if (! empty($conf->stripe->enabled))
{
$permissiontowrite = $user->rights->societe->creer;
// Stripe customer key 'cu_....' stored into llx_societe_account
print '<tr><td class="titlefield">'.$langs->trans('StripeCustomerId').'</td><td>';
print $stripecu;
print '<tr><td class="titlefield">';
//print $langs->trans('StripeCustomerId');
print $form->editfieldkey("StripeCustomerId", 'key_account', $stripecu, $object, $permissiontowrite, 'string', '', 0, 1, 'socid');
print '</td><td>';
//print $stripecu;
print $form->editfieldval("StripeCustomerId", 'key_account', $stripecu, $object, $permissiontowrite, 'string', '', null, null, '', 1, '', 'socid');
print '</td></tr>';
}
print '</table>';
@@ -475,24 +534,30 @@ if ($socid && $action != 'edit' && $action != "create")
if (! (empty($conf->stripe->enabled)))
{
print load_fiche_titre($langs->trans('StripeGateways').($stripeacc ? ' ('.$stripeacc.')':''), '', '');
print load_fiche_titre($langs->trans('StripePaymentModes').($stripeacc ? ' ('.$stripeacc.')':''), '', '');
$listofsources = array();
if (is_object($stripe) && $stripeacc)
{
$customerstripe=$stripe->customerStripe($object->id, $stripeacc, $servicestatus);
if ($customerstripe->id) {
$listofsources=$customerstripe->sources->data;
try {
$customerstripe=$stripe->customerStripe($object->id, $stripeacc, $servicestatus);
if ($customerstripe->id) {
$listofsources=$customerstripe->sources->data;
}
}
catch(Exception $e)
{
dol_syslog("Failed to get strip customer for thirdparty id =".$object->id);
}
}
print '<div class="div-table-responsive-no-min">'; // You can use div-table-responsive-no-min if you dont need reserved height for your table
print '<table class="liste" width="100%">'."\n";
print '<tr class="liste_titre">';
print '<td align="left">'.$langs->trans('Type').'</td>';
print '<td align="left">'.$langs->trans('Informations').'</td>';
print '<td align="left"></td>';
print '<td>'.$langs->trans('ID').'</td>';
print '<td>'.$langs->trans('Type').'</td>';
print '<td>'.$langs->trans('Informations').'</td>';
print '<td></td>';
print '<td align="center">'.$langs->trans('Default').'</td>';
print "<td></td></tr>\n";
@@ -500,7 +565,10 @@ if ($socid && $action != 'edit' && $action != "create")
{
foreach ($listofsources as $src)
{
print '<tr>';
print '<tr class="oddeven">';
print '<td>';
print $src->id;
print '</td>';
print '<td>';
if ($src->object=='card')
{
@@ -511,7 +579,7 @@ if ($socid && $action != 'edit' && $action != "create")
elseif ($src->brand == 'JCB') {$brand='cc-jcb';}
elseif ($src->brand == 'Diners Club') {$brand='cc-diners-club';}
else {$brand='credit-card';}
print '<span class="fa fa-'.$brand.' fa-3x fa-fw"></span>';
print '<span class="fa fa-'.$brand.' fa-2x fa-fw"></span>';
}
elseif ($src->object=='source' && $src->type=='card')
{
@@ -522,11 +590,11 @@ if ($socid && $action != 'edit' && $action != "create")
elseif ($src->card->brand == 'JCB') {$brand='cc-jcb';}
elseif ($src->card->brand == 'Diners Club') {$brand='cc-diners-club';}
else {$brand='credit-card';}
print '<span class="fa fa-'.$brand.' fa-3x fa-fw"></span>';
print '<span class="fa fa-'.$brand.' fa-2x fa-fw"></span>';
}
elseif ($src->object=='source' && $src->type=='sepa_debit')
{
print '<span class="fa fa-university fa-3x fa-fw"></span>';
print '<span class="fa fa-university fa-2x fa-fw"></span>';
}
print'</td><td valign="middle">';
@@ -570,13 +638,13 @@ if ($socid && $action != 'edit' && $action != "create")
print '</td>';
// Default
print '<td align="center" width="50">';
if (($cu->default_source!=$src->id))
if (($customerstripe->default_source != $src->id))
{
print '<a href="' . DOL_URL_ROOT.'/societe/paymentmodes.php?socid='.$object->id.'&source='.$src->id.'&action=setassourcedefault">';
print "<SPAN class='fa fa-circle fa-2x'></SPAN>";
print img_picto($langs->trans("Default"),'off');
print '</a>';
} else {
print "<SPAN class=' fa fa-check-circle fa-2x'></SPAN>";
print img_picto($langs->trans("Default"),'on');
}
print '</td>';
print '<td align="center">';
@@ -587,7 +655,7 @@ if ($socid && $action != 'edit' && $action != "create")
// print '</a>';
// print '&nbsp;';
print '<a href="' . DOL_URL_ROOT.'/societe/paymentmodes.php?socid='.$object->id.'&source='.$src->id.'&action=delete">';
print "<SPAN class='fa fa-trash fa-2x'></SPAN>";
print img_delete($langs->trans("Delete"));
print '</a>';
}
print '</td></tr>';
@@ -603,8 +671,9 @@ if ($socid && $action != 'edit' && $action != "create")
// List of bank accounts
print '<br>';
$morehtmlright='<a href="'.$_SERVER["PHP_SELF"].'?socid='.$object->id.'&amp;action=create">'.$langs->trans("Add").'</a>';
$morehtmlright='<a class="butAction" href="'.$_SERVER["PHP_SELF"].'?socid='.$object->id.'&amp;action=create">'.$langs->trans("Add").'</a>';
print load_fiche_titre($langs->trans("AllRIB"), $morehtmlright, '');