fetch greatest tms for user and fix user creation and modification (#35145)

* fetch greatest tms for user and fix user creation and modification

* fetch greatest tms for user and fix user creation and modification

* fetch greatest tms for user and fix user creation and modification

* fetch greatest tms for user and fix user creation and modification

* fetch greatest tms for user and fix user creation and modification

* fetch greatest tms for user and fix user creation and modification
This commit is contained in:
Frédéric FRANCE 2025-09-01 19:21:54 +02:00 committed by GitHub
parent 44ccc0f284
commit 34498d3437
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
4 changed files with 93 additions and 53 deletions

View file

@ -550,9 +550,10 @@ class User extends CommonObject
$sql .= " u.admin, u.login, u.note_private, u.note_public,";
$sql .= " u.pass, u.pass_crypted, u.pass_temp, u.api_key,";
$sql .= " u.fk_soc, u.fk_socpeople, u.fk_member, u.fk_user, u.ldap_sid, u.fk_user_expense_validator, u.fk_user_holiday_validator,";
$sql .= " fk_user_creat as user_creation_id, fk_user_modif as user_modification_id,";
$sql .= " u.statut as status, u.lang, u.entity,";
$sql .= " u.datec as datec,";
$sql .= " u.tms as datem,";
$sql .= " GREATEST(u.tms, uef.tms) as datem,";
$sql .= " u.datelastlogin as datel,";
$sql .= " u.datepreviouslogin as datep,";
$sql .= " u.flagdelsessionsbefore,";
@ -581,6 +582,7 @@ class User extends CommonObject
$sql .= " d.code_departement as state_code, d.nom as state,";
$sql .= " s.label as label_establishment, u.fk_establishment";
$sql .= " FROM ".$this->db->prefix()."user as u";
$sql .= " LEFT JOIN ".$this->db->prefix()."user_extrafields as uef ON uef.fk_object = u.rowid";
$sql .= " LEFT JOIN ".$this->db->prefix()."c_country as c ON u.fk_country = c.rowid";
$sql .= " LEFT JOIN ".$this->db->prefix()."c_departements as d ON u.fk_state = d.rowid";
$sql .= " LEFT JOIN ".$this->db->prefix()."establishment as s ON u.fk_establishment = s.rowid";
@ -658,55 +660,57 @@ class User extends CommonObject
$this->employee = $obj->employee;
$this->login = $obj->login;
$this->gender = $obj->gender;
$this->birth = $this->db->jdate($obj->birth);
$this->gender = $obj->gender;
$this->birth = $this->db->jdate($obj->birth);
$this->pass_indatabase = $obj->pass;
$this->pass_indatabase_crypted = $obj->pass_crypted;
$this->pass = $obj->pass;
$this->pass_temp = $obj->pass_temp;
$this->pass_temp = $obj->pass_temp;
$this->datelastpassvalidation = $obj->datelastpassvalidation;
$this->api_key = dolDecrypt($obj->api_key);
$this->address = $obj->address;
$this->zip = $obj->zip;
$this->town = $obj->town;
$this->address = $obj->address;
$this->zip = $obj->zip;
$this->town = $obj->town;
$this->country_id = $obj->country_id;
$this->country_code = $obj->country_id ? $obj->country_code : '';
//$this->country = $obj->country_id?($langs->trans('Country'.$obj->country_code)!='Country'.$obj->country_code?$langs->transnoentities('Country'.$obj->country_code):$obj->country):'';
$this->state_id = $obj->state_id;
$this->state_code = $obj->state_code;
$this->state = ($obj->state != '-' ? $obj->state : '');
$this->state_id = $obj->state_id;
$this->state_code = $obj->state_code;
$this->state = ($obj->state != '-' ? $obj->state : '');
$this->office_phone = $obj->office_phone;
$this->office_fax = $obj->office_fax;
$this->user_mobile = $obj->user_mobile;
$this->office_phone = $obj->office_phone;
$this->office_fax = $obj->office_fax;
$this->user_mobile = $obj->user_mobile;
$this->personal_mobile = $obj->personal_mobile;
$this->email = $obj->email;
$this->email_oauth2 = $obj->email_oauth2;
$this->personal_email = $obj->personal_email;
$this->socialnetworks = ($obj->socialnetworks ? (array) json_decode($obj->socialnetworks, true) : array());
$this->user_creation_id = $obj->user_creation_id;
$this->user_modification_id = $obj->user_modification_id;
$this->job = $obj->job;
$this->signature = $obj->signature;
$this->admin = $obj->admin;
$this->admin = $obj->admin;
$this->note_public = $obj->note_public;
$this->note_private = $obj->note_private;
$this->statut = $obj->status; // deprecated
$this->status = $obj->status;
$this->statut = $obj->status; // deprecated
$this->status = $obj->status;
$this->photo = $obj->photo;
$this->openid = $obj->openid;
$this->lang = $obj->lang;
$this->entity = $obj->entity;
$this->photo = $obj->photo;
$this->openid = $obj->openid;
$this->lang = $obj->lang;
$this->entity = $obj->entity;
$this->accountancy_code_user_general = $obj->accountancy_code_user_general;
$this->accountancy_code = $obj->accountancy_code;
$this->thm = $obj->thm;
$this->tjm = $obj->tjm;
$this->thm = $obj->thm;
$this->tjm = $obj->tjm;
$this->salary = $obj->salary;
$this->salaryextra = $obj->salaryextra;
$this->weeklyhours = $obj->weeklyhours;
@ -714,8 +718,8 @@ class User extends CommonObject
$this->dateemployment = $this->db->jdate($obj->dateemployment);
$this->dateemploymentend = $this->db->jdate($obj->dateemploymentend);
$this->datec = $this->db->jdate($obj->datec);
$this->datem = $this->db->jdate($obj->datem);
$this->datec = $this->db->jdate($obj->datec);
$this->datem = $this->db->jdate($obj->datem);
$this->datelastlogin = $this->db->jdate($obj->datel);
$this->datepreviouslogin = $this->db->jdate($obj->datep);
$this->flagdelsessionsbefore = $this->db->jdate($obj->flagdelsessionsbefore, 'gmt');
@ -724,9 +728,9 @@ class User extends CommonObject
$this->datestartvalidity = $this->db->jdate($obj->datestartvalidity);
$this->dateendvalidity = $this->db->jdate($obj->dateendvalidity);
$this->socid = $obj->fk_soc;
$this->contact_id = $obj->fk_socpeople;
$this->fk_member = $obj->fk_member;
$this->socid = $obj->fk_soc;
$this->contact_id = $obj->fk_socpeople;
$this->fk_member = $obj->fk_member;
$this->fk_user = $obj->fk_user;
$this->fk_user_expense_validator = $obj->fk_user_expense_validator;
$this->fk_user_holiday_validator = $obj->fk_user_holiday_validator;
@ -1749,6 +1753,7 @@ class User extends CommonObject
$this->civility_code = trim((string) $this->civility_code);
$this->login = trim((string) $this->login);
$this->user_creation_id = (int) $user->id;
if (!isset($this->entity)) {
$this->entity = $conf->entity; // If not defined, we use default value
}
@ -1810,8 +1815,8 @@ class User extends CommonObject
}
// Insert into database
$sql = "INSERT INTO ".$this->db->prefix()."user (datec, login, ldap_sid, entity)";
$sql .= " VALUES('".$this->db->idate($this->datec)."', '".$this->db->escape($this->login)."', '".$this->db->escape($this->ldap_sid)."', ".((int) $this->entity).")";
$sql = "INSERT INTO ".$this->db->prefix()."user (datec, login, ldap_sid, fk_user_creat, entity)";
$sql .= " VALUES('".$this->db->idate($this->datec)."', '".$this->db->escape($this->login)."', '".$this->db->escape($this->ldap_sid)."', ".(int) $this->user_creation_id.", ".((int) $this->entity).")";
$result = $this->db->query($sql);
dol_syslog(get_class($this)."::create", LOG_DEBUG);
@ -2122,7 +2127,7 @@ class User extends CommonObject
$this->lastname = trim((string) $this->lastname);
$this->firstname = trim((string) $this->firstname);
$this->ref_employee = trim((string) $this->ref_employee);
$this->national_registration_number = trim((string) $this->national_registration_number);
$this->national_registration_number = trim((string) $this->national_registration_number);
$this->employee = ($this->employee > 0 ? $this->employee : 0);
$this->login = trim((string) $this->login);
$this->gender = trim((string) $this->gender);
@ -2151,8 +2156,9 @@ class User extends CommonObject
$this->note_private = trim((string) $this->note_private);
$this->openid = trim((string) $this->openid);
$this->admin = ($this->admin > 0 ? $this->admin : 0);
$this->user_modification_id = $user->id;
$this->accountancy_code_user_general = trim((string) $this->accountancy_code_user_general);
$this->accountancy_code_user_general = trim((string) $this->accountancy_code_user_general);
$this->accountancy_code = trim((string) $this->accountancy_code);
$this->color = trim((string) $this->color);
$this->dateemployment = empty($this->dateemployment) ? '' : $this->dateemployment;
@ -2255,6 +2261,7 @@ class User extends CommonObject
$sql .= ", photo = ".($this->photo ? "'".$this->db->escape($this->photo)."'" : "null");
$sql .= ", openid = ".($this->openid ? "'".$this->db->escape($this->openid)."'" : "null");
$sql .= ", fk_user = ".($this->fk_user > 0 ? "'".((int) $this->fk_user)."'" : "null");
$sql .= ", fk_user_modif = ".($this->user_modification_id > 0 ? "'".((int) $this->user_modification_id)."'" : "null");
$sql .= ", fk_user_expense_validator = ".($this->fk_user_expense_validator > 0 ? "'".((int) $this->fk_user_expense_validator)."'" : "null");
$sql .= ", fk_user_holiday_validator = ".($this->fk_user_holiday_validator > 0 ? "'".((int) $this->fk_user_holiday_validator)."'" : "null");
if (isset($this->thm) || $this->thm != '') {
@ -3608,6 +3615,7 @@ class User extends CommonObject
$this->id = 0;
$this->ref = 'SPECIMEN';
$this->specimen = 1;
$this->user_creation_id = $user->id;
$this->lastname = 'DOLIBARR';
$this->firstname = 'SPECIMEN';
@ -3638,7 +3646,6 @@ class User extends CommonObject
$this->iplastlogin = '127.0.0.1';
$this->datepreviouslogin = $now;
$this->ippreviouslogin = '127.0.0.1';
$this->statut = 1; // deprecated
$this->status = 1;
$this->entity = 1;
@ -3654,9 +3661,10 @@ class User extends CommonObject
*/
public function info($id)
{
$sql = "SELECT u.rowid, u.login as ref, u.datec,";
$sql .= " u.tms as date_modification, u.entity";
$sql = "SELECT u.rowid, u.login as ref, u.datec, fk_user_creat as user_creation_id, fk_user_modif as user_modification_id,";
$sql .= " GREATEST(u.tms, uef.tms) as date_modification, u.entity";
$sql .= " FROM ".$this->db->prefix()."user as u";
$sql .= " LEFT JOIN ".$this->db->prefix()."user_extrafields as uef ON uef.fk_object = u.rowid";
$sql .= " WHERE u.rowid = ".((int) $id);
$result = $this->db->query($sql);
@ -3666,6 +3674,9 @@ class User extends CommonObject
$this->id = $obj->rowid;
$this->user_creation_id = $obj->user_creation_id;
$this->user_modification_id = $obj->user_modification_id;
$this->ref = (!$obj->ref) ? $obj->rowid : $obj->ref;
$this->date_creation = $this->db->jdate($obj->datec);
$this->date_modification = $this->db->jdate($obj->date_modification);

View file

@ -1,8 +1,8 @@
<?php
/* Copyright (C) 2005-2018 Laurent Destailleur <eldy@users.sourceforge.net>
* Copyright (C) 2005-2024 Regis Houssin <regis.houssin@inodbox.com>
* Copyright (C) 2019 Nicolas ZABOURI <info@inovea-conseil.com>
* Copyright (C) 2024 Frédéric France <frederic.france@free.fr>
/* Copyright (C) 2005-2018 Laurent Destailleur <eldy@users.sourceforge.net>
* Copyright (C) 2005-2024 Regis Houssin <regis.houssin@inodbox.com>
* Copyright (C) 2019 Nicolas ZABOURI <info@inovea-conseil.com>
* Copyright (C) 2024-2025 Frédéric France <frederic.france@free.fr>
*
* 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

View file

@ -7,7 +7,7 @@
* Copyright (C) 2024-2025 MDW <mdeweerd@users.noreply.github.com>
* Copyright (C) 2024 Benjamin Falière <benjamin.faliere@altairis.fr>
* Copyright (C) 2024 William Mead <william.mead@manchenumerique.fr>
* Copyright (C) 2024 Frédéric France <frederic.france@free.fr>
* Copyright (C) 2024-2025 Frédéric France <frederic.france@free.fr>
*
* 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
@ -154,7 +154,7 @@ $arrayfields = array(
'u.job' => array('label' => "PostOrFunction", 'checked' => '-1', 'position' => 60),
'u.salary' => array('label' => "Salary", 'checked' => '-1', 'position' => 80, 'enabled' => (string) (int) (isModEnabled('salaries') && $user->hasRight("salaries", "readall")), 'isameasure' => 1),
'u.datec' => array('label' => "DateCreation", 'checked' => '0', 'position' => 500),
'u.tms' => array('label' => "DateModificationShort", 'checked' => '0', 'position' => 500),
'date_modification' => array('label' => "DateModificationShort", 'checked' => '0', 'position' => 500),
'u.statut' => array('label' => "Status", 'checked' => '1', 'position' => 1000),
);
@ -392,7 +392,7 @@ $sql .= " u.fk_user,";
$sql .= " u.ref_employee, u.national_registration_number, u.job, u.salary, u.datelastlogin, u.datepreviouslogin,";
$sql .= " u.datestartvalidity, u.dateendvalidity,";
$sql .= " u.ldap_sid, u.statut as status, u.entity,";
$sql .= " u.tms as date_modification, u.datec as date_creation,";
$sql .= " GREATEST(u.tms, ef.tms) as date_modification, u.datec as date_creation,";
$sql .= " u2.rowid as id2, u2.login as login2, u2.firstname as firstname2, u2.lastname as lastname2, u2.admin as admin2, u2.fk_soc as fk_soc2, u2.office_phone as ofice_phone2, u2.user_mobile as user_mobile2, u2.email as email2, u2.gender as gender2, u2.photo as photo2, u2.entity as entity2, u2.statut as status2,";
$sql .= " s.nom as name, s.canvas,";
$sql .= " co.code as country_code, co.label as country_label";
@ -411,9 +411,7 @@ $sql = preg_replace('/,\s*$/', '', $sql);
$sqlfields = $sql; // $sql fields to remove for count total
$sql .= " FROM ".MAIN_DB_PREFIX.$object->table_element." as u";
if (isset($extrafields->attributes[$object->table_element]['label']) && is_array($extrafields->attributes[$object->table_element]['label']) && count($extrafields->attributes[$object->table_element]['label'])) {
$sql .= " LEFT JOIN ".MAIN_DB_PREFIX.$object->table_element."_extrafields as ef on (u.rowid = ef.fk_object)";
}
$sql .= " LEFT JOIN ".MAIN_DB_PREFIX.$object->table_element."_extrafields as ef on (u.rowid = ef.fk_object)";
$sql .= " LEFT JOIN ".MAIN_DB_PREFIX."societe as s ON u.fk_soc = s.rowid";
$sql .= " LEFT JOIN ".MAIN_DB_PREFIX."user as u2 ON u.fk_user = u2.rowid";
$sql .= " LEFT JOIN ".MAIN_DB_PREFIX."c_country as co ON u.fk_country = co.rowid";
@ -863,7 +861,7 @@ if (!empty($arrayfields['u.datec']['checked'])) {
print '<td class="liste_titre">';
print '</td>';
}
if (!empty($arrayfields['u.tms']['checked'])) {
if (!empty($arrayfields['date_modification']['checked'])) {
// Date modification
print '<td class="liste_titre">';
print '</td>';
@ -988,8 +986,8 @@ if (!empty($arrayfields['u.datec']['checked'])) {
print_liste_field_titre("DateCreationShort", $_SERVER["PHP_SELF"], "u.datec", "", $param, '', $sortfield, $sortorder, 'center nowrap ');
$totalarray['nbfield']++;
}
if (!empty($arrayfields['u.tms']['checked'])) {
print_liste_field_titre("DateModificationShort", $_SERVER["PHP_SELF"], "u.tms", "", $param, '', $sortfield, $sortorder, 'center nowrap ');
if (!empty($arrayfields['date_modification']['checked'])) {
print_liste_field_titre("DateModificationShort", $_SERVER["PHP_SELF"], "date_modification", "", $param, '', $sortfield, $sortorder, 'center nowrap ');
$totalarray['nbfield']++;
}
if (!empty($arrayfields['u.statut']['checked'])) {
@ -1376,7 +1374,7 @@ while ($i < $imaxinloop) {
}
}
// Date modification
if (!empty($arrayfields['u.tms']['checked'])) {
if (!empty($arrayfields['date_modification']['checked'])) {
print '<td class="center nowraponall">';
print dol_print_date($db->jdate($obj->date_modification), 'dayhour', 'tzuser');
print '</td>';

View file

@ -1,8 +1,8 @@
<?php
/* Copyright (C) 2010-2015 Laurent Destailleur <eldy@users.sourceforge.net>
* Copyright (C) 2023 Alexandre Janniaux <alexandre.janniaux@gmail.com>
* Copyright (C) 2024 MDW <mdeweerd@users.noreply.github.com>
* Copyright (C) 2024 Frédéric France <frederic.france@free.fr>
/* Copyright (C) 2010-2015 Laurent Destailleur <eldy@users.sourceforge.net>
* Copyright (C) 2023 Alexandre Janniaux <alexandre.janniaux@gmail.com>
* Copyright (C) 2024 MDW <mdeweerd@users.noreply.github.com>
* Copyright (C) 2024-2025 Frédéric France <frederic.france@free.fr>
*
* 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
@ -144,7 +144,38 @@ class UserTest extends CommonClassTest
$newlocalobject->initAsSpecimen();
$this->changeProperties($newlocalobject); // Change some properties int $newlocalobject
$this->assertEquals($this->objCompare($localobject, $newlocalobject, true, array('array_options','id','socid','societe_id','specimen','note','ref','pass','pass_indatabase','pass_indatabase_crypted','pass_temp','datec','datem','datelastlogin','datepreviouslogin','datelastpassvalidation','flagdelsessionsbefore','iplastlogin','ippreviouslogin','trackid')), array()); // Actual, Expected
$this->assertEquals(
$this->objCompare( // Actual, Expected
$localobject,
$newlocalobject,
true,
array(
'array_options',
'id',
'socid',
'societe_id',
'specimen',
'statut',
'user_modification_id',
'note',
'ref',
'pass',
'pass_indatabase',
'pass_indatabase_crypted',
'pass_temp',
'datec',
'datem',
'datelastlogin',
'datepreviouslogin',
'datelastpassvalidation',
'flagdelsessionsbefore',
'iplastlogin',
'ippreviouslogin',
'trackid'
)
),
array()
);
return $localobject;
}