Passed
Pull Request — dev (#8)
by Rafael
58:47
created

Account::getNomUrl()   F

Complexity

Conditions 30
Paths > 20000

Size

Total Lines 80
Code Lines 54

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 30
eloc 54
nc 43200
nop 6
dl 0
loc 80
rs 0
c 0
b 0
f 0

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
/* Copyright (C) 2001-2007  Rodolphe Quiedeville        <[email protected]>
4
 * Copyright (C) 2003		Jean-Louis Bergamo		    <[email protected]>
5
 * Copyright (C) 2004-2012	Laurent Destailleur		    <[email protected]>
6
 * Copyright (C) 2004		Christophe Combelles	    <[email protected]>
7
 * Copyright (C) 2005-2010	Regis Houssin			    <[email protected]>
8
 * Copyright (C) 2013		Florian Henry			    <[email protected]>
9
 * Copyright (C) 2015-2016	Marcos García			    <[email protected]>
10
 * Copyright (C) 2015-2017	Alexandre Spangaro		    <[email protected]>
11
 * Copyright (C) 2016		Ferran Marcet   		    <[email protected]>
12
 * Copyright (C) 2019		JC Prieto				    <[email protected]><[email protected]>
13
 * Copyright (C) 2022-2024  Frédéric France             <[email protected]>
14
 * Copyright (C) 2024		MDW							<[email protected]>
15
 * Copyright (C) 2024       Rafael San José             <[email protected]>
16
 *
17
 * This program is free software; you can redistribute it and/or modify
18
 * it under the terms of the GNU General Public License as published by
19
 * the Free Software Foundation; either version 3 of the License, or
20
 * (at your option) any later version.
21
 *
22
 * This program is distributed in the hope that it will be useful,
23
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
24
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
25
 * GNU General Public License for more details.
26
 *
27
 * You should have received a copy of the GNU General Public License
28
 * along with this program. If not, see <https://www.gnu.org/licenses/>.
29
 */
30
31
namespace Dolibarr\Code\Compta\Classes;
32
33
use Dolibarr\Code\Categories\Classes\Categorie;
34
use Dolibarr\Code\Core\Classes\WorkboardResponse;
35
use Dolibarr\Code\Societe\Classes\Societe;
36
use Dolibarr\Code\User\Classes\User;
37
use Dolibarr\Core\Base\CommonObject;
38
use DoliDB;
39
40
/**
41
 *  \file       htdocs/compta/bank/class/account.class.php
42
 *  \ingroup    bank
43
 *  \brief      File of class to manage bank accounts
44
 */
45
46
/**
47
 *  Class to manage bank accounts
48
 */
49
class Account extends CommonObject
50
{
51
    /**
52
     * @var string ID to identify managed object
53
     */
54
    public $element = 'bank_account';
55
56
    /**
57
     * @var string Name of table without prefix where object is stored
58
     */
59
    public $table_element = 'bank_account';
60
61
    /**
62
     * @var string String with name of icon for myobject. Must be the part after the 'object_' into object_myobject.png
63
     */
64
    public $picto = 'account';
65
66
    /**
67
     * @var int     Use id instead of rowid
68
     * @deprecated
69
     * @see $id
70
     */
71
    public $rowid;
72
73
    /**
74
     * Account Label
75
     * @var string
76
     */
77
    public $label;
78
79
    /**
80
     * Bank account type. Check TYPE_ constants
81
     * @var int
82
     * @deprecated
83
     * @see $type
84
     */
85
    private $courant; // @phpstan-ignore-line
86
87
    /**
88
     * Bank account type. Check TYPE_ constants. It's integer but Company bank account use string to identify type account
89
     * @var int|string
90
     */
91
    public $type;
92
93
    /**
94
     * Bank name
95
     * @var string
96
     */
97
    public $bank;
98
99
    /**
100
     * Status closed
101
     *
102
     * @var int
103
     * @deprecated  Duplicate field. We already have the field $this->status
104
     * @see $status
105
     */
106
    private $clos = self::STATUS_OPEN;
107
108
    /**
109
     * Does it need to be conciliated?
110
     * @var int
111
     */
112
    public $rappro = 1;
113
114
    /**
115
     * Webpage
116
     * @var string
117
     */
118
    public $url;
119
120
    /**
121
     * Bank number. If in SEPA area, you should move to IBAN field
122
     * @var string
123
     */
124
    public $code_banque;
125
126
    /**
127
     * Branch number. If in SEPA area, you should move to IBAN field
128
     * @var string
129
     */
130
    public $code_guichet;
131
132
    /**
133
     * Account number. If in SEPA area, you should move to IBAN field
134
     * @var string
135
     */
136
    public $number;
137
138
    /**
139
     * Bank account number control digit. If in SEPA area, you should move to IBAN field
140
     * @var string
141
     */
142
    public $cle_rib;
143
144
    /**
145
     * BIC/Swift code
146
     * @var string
147
     */
148
    public $bic;
149
150
    /**
151
     * IBAN number (International Bank Account Number). Stored into iban_prefix field into database (TODO Rename field in database)
152
     * @var string
153
     */
154
    public $iban;
155
156
    /**
157
     * IBAN number
158
     *
159
     * @var string
160
     * @deprecated see $iban
161
     */
162
    public $iban_prefix;
163
164
    /**
165
     * XML SEPA format: place Payment Type Information (PmtTpInf) in Credit Transfer Transaction Information (CdtTrfTxInf)
166
     * @var int
167
     */
168
    public $pti_in_ctti = 0;
169
170
    /**
171
     * Name of account holder
172
     * @var string
173
     * @deprecated
174
     * @see $owner_name
175
     */
176
    private $proprio;
177
178
    /**
179
     * Name of account holder
180
     * @var string
181
     */
182
    public $owner_name;
183
184
    /**
185
     * Address of account holder
186
     * @var string
187
     */
188
    public $owner_address;
189
190
    /**
191
     * Zip of account holder
192
     * @var string
193
     */
194
    public $owner_zip;
195
196
    /**
197
     * Town of account holder
198
     * @var string
199
     */
200
    public $owner_town;
201
    public $owner_country_id;
202
    public $owner_country_code;
203
204
    /**
205
     * Address of the bank account
206
     * @var string
207
     * @deprecated
208
     * @see $address
209
     */
210
    private $domiciliation;
211
212
    /**
213
     * Address of the bank account
214
     * @var string
215
     */
216
    public $address;
217
    public $state_id;
218
    public $state_code;
219
    public $state;
220
    public $country_id;
221
222
    /**
223
     * Variable containing all account types with their respective translated label.
224
     * Defined in __construct
225
     * @var array
226
     */
227
    public $type_lib = array();
228
229
    /**
230
     * Accountancy code
231
     * @var string
232
     */
233
    public $account_number;
234
235
    /**
236
     * @var int ID
237
     */
238
    public $fk_accountancy_journal;
239
240
    /**
241
     * @var string  Label of journal
242
     */
243
    public $accountancy_journal;
244
245
    /**
246
     * Currency code
247
     * @var string
248
     */
249
    public $currency_code;
250
251
    /**
252
     * Currency code
253
     * @var string
254
     * @deprecated Use currency_code instead
255
     * @see $currency_code
256
     */
257
    public $account_currency_code;
258
259
    /**
260
     * Authorized minimum balance
261
     * @var float
262
     */
263
    public $min_allowed;
264
265
    /**
266
     * Desired minimum balance
267
     * @var float
268
     */
269
    public $min_desired;
270
271
    /**
272
     * Notes
273
     * @var string
274
     */
275
    public $comment;
276
277
    /**
278
     * Date of the initial balance. Used in Account::create
279
     * @var int
280
     */
281
    public $date_solde;
282
283
    /**
284
     * Balance. Used in Account::create
285
     * @var float
286
     * @deprecated
287
     * @see $balance
288
     */
289
    private $solde; // @phpstan-ignore-line
290
291
    /**
292
     * Balance. Used in Account::create
293
     * @var float
294
     */
295
    public $balance;
296
297
    /**
298
     * Creditor Identifier CI. Some banks use different ICS for direct debit and bank transfer
299
     * @var string
300
     */
301
    public $ics;
302
303
    /**
304
     * Creditor Identifier for Bank Transfer.
305
     * @var string
306
     */
307
    public $ics_transfer;
308
309
310
    /**
311
     *  'type' if the field format ('integer', 'integer:ObjectClass:PathToClass[:AddCreateButtonOrNot[:Filter]]', 'varchar(x)', 'double(24,8)', 'real', 'price', 'text', 'html', 'date', 'datetime', 'timestamp', 'duration', 'mail', 'phone', 'url', 'password')
312
     *         Note: Filter can be a string like "(t.ref:like:'SO-%') or (t.date_creation:<:'20160101') or (t.nature:is:NULL)"
313
     *  'label' the translation key.
314
     *  'enabled' is a condition when the field must be managed.
315
     *  'position' is the sort order of field.
316
     *  'notnull' is set to 1 if not null in database. Set to -1 if we must set data to null if empty ('' or 0).
317
     *  'visible' says if field is visible in list (Examples: 0=Not visible, 1=Visible on list and create/update/view forms, 2=Visible on list only, 3=Visible on create/update/view form only (not list), 4=Visible on list and update/view form only (not create). 5=Visible on list and view only (not create/not update). Using a negative value means field is not shown by default on list but can be selected for viewing)
318
     *  'noteditable' says if field is not editable (1 or 0)
319
     *  'default' is a default value for creation (can still be overwrote by the Setup of Default Values if field is editable in creation form). Note: If default is set to '(PROV)' and field is 'ref', the default value will be set to '(PROVid)' where id is rowid when a new record is created.
320
     *  'index' if we want an index in database.
321
     *  'foreignkey'=>'tablename.field' if the field is a foreign key (it is recommended to name the field fk_...).
322
     *  'searchall' is 1 if we want to search in this field when making a search from the quick search button.
323
     *  'isameasure' must be set to 1 if you want to have a total on list for this field. Field type must be summable like integer or double(24,8).
324
     *  'css' is the CSS style to use on field. For example: 'maxwidth200'
325
     *  'help' is a string visible as a tooltip on field
326
     *  'showoncombobox' if value of the field must be visible into the label of the combobox that list record
327
     *  'disabled' is 1 if we want to have the field locked by a 'disabled' attribute. In most cases, this is never set into the definition of $fields into class, but is set dynamically by some part of code.
328
     *  'arrayofkeyval' to set list of value if type is a list of predefined values. For example: array("0"=>"Draft","1"=>"Active","-1"=>"Cancel")
329
     *  'comment' is not used. You can store here any text of your choice. It is not used by application.
330
     *
331
     *  Note: To have value dynamic, you can set value to 0 in definition and edit the value on the fly into the constructor.
332
     */
333
334
    // BEGIN MODULEBUILDER PROPERTIES
335
    /**
336
     * @var array<string,array{type:string,label:string,enabled:int<0,2>|string,position:int,notnull?:int,visible:int,noteditable?:int,default?:string,index?:int,foreignkey?:string,searchall?:int,isameasure?:int,css?:string,csslist?:string,help?:string,showoncombobox?:int,disabled?:int,arrayofkeyval?:array<int,string>,comment?:string}>  Array with all fields and their property. Do not use it as a static var. It may be modified by constructor.
0 ignored issues
show
Documentation Bug introduced by
The doc comment array<string,array{type:...ring>,comment?:string}> at position 16 could not be parsed: Expected '}' at position 16, but found 'int'.
Loading history...
337
     */
338
    public $fields = array(
339
        'rowid' => array('type' => 'integer', 'label' => 'TechnicalID', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'position' => 10),
340
        'ref' => array('type' => 'varchar(12)', 'label' => 'Ref', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'showoncombobox' => 1, 'position' => 25),
341
        'label' => array('type' => 'varchar(30)', 'label' => 'Label', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'position' => 30),
342
        'entity' => array('type' => 'integer', 'label' => 'Entity', 'default' => '1', 'enabled' => 1, 'visible' => -2, 'notnull' => 1, 'position' => 35, 'index' => 1),
343
        'bank' => array('type' => 'varchar(60)', 'label' => 'Bank', 'enabled' => 1, 'visible' => -1, 'position' => 40),
344
        'code_banque' => array('type' => 'varchar(128)', 'label' => 'Code banque', 'enabled' => 1, 'visible' => -1, 'position' => 45),
345
        'code_guichet' => array('type' => 'varchar(6)', 'label' => 'Code guichet', 'enabled' => 1, 'visible' => -1, 'position' => 50),
346
        'number' => array('type' => 'varchar(255)', 'label' => 'Number', 'enabled' => 1, 'visible' => -1, 'position' => 55),
347
        'cle_rib' => array('type' => 'varchar(5)', 'label' => 'Cle rib', 'enabled' => 1, 'visible' => -1, 'position' => 60),
348
        'bic' => array('type' => 'varchar(11)', 'label' => 'Bic', 'enabled' => 1, 'visible' => -1, 'position' => 65),
349
        'iban_prefix' => array('type' => 'varchar(34)', 'label' => 'Iban prefix', 'enabled' => 1, 'visible' => -1, 'position' => 70),
350
        'country_iban' => array('type' => 'varchar(2)', 'label' => 'Country iban', 'enabled' => 1, 'visible' => -1, 'position' => 75),
351
        'cle_iban' => array('type' => 'varchar(2)', 'label' => 'Cle iban', 'enabled' => 1, 'visible' => -1, 'position' => 80),
352
        'domiciliation' => array('type' => 'varchar(255)', 'label' => 'Domiciliation', 'enabled' => 1, 'visible' => -1, 'position' => 85),
353
        'state_id' => array('type' => 'integer', 'label' => 'StateId', 'enabled' => 1, 'visible' => -1, 'position' => 90),
354
        'fk_pays' => array('type' => 'integer', 'label' => 'Country', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'position' => 95),
355
        'proprio' => array('type' => 'varchar(60)', 'label' => 'Proprio', 'enabled' => 1, 'visible' => -1, 'position' => 100),
356
        'owner_address' => array('type' => 'varchar(255)', 'label' => 'Owner address', 'enabled' => 1, 'visible' => -1, 'position' => 105),
357
        'owner_zip' => array('type' => 'varchar(25)', 'label' => 'Owner zip', 'enabled' => 1, 'visible' => -1, 'position' => 106),
358
        'owner_town' => array('type' => 'varchar(50)', 'label' => 'Owner town', 'enabled' => 1, 'visible' => -1, 'position' => 107),
359
        'owner_country_id' => array('type' => 'integer', 'label' => 'Owner country', 'enabled' => 1, 'visible' => -1, 'position' => 108),
360
        'courant' => array('type' => 'smallint(6)', 'label' => 'Courant', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'position' => 110),
361
        'clos' => array('type' => 'smallint(6)', 'label' => 'Clos', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'position' => 115),
362
        'rappro' => array('type' => 'smallint(6)', 'label' => 'Rappro', 'enabled' => 1, 'visible' => -1, 'position' => 120),
363
        'url' => array('type' => 'varchar(128)', 'label' => 'Url', 'enabled' => 1, 'visible' => -1, 'position' => 125),
364
        'account_number' => array('type' => 'varchar(32)', 'label' => 'Account number', 'enabled' => 1, 'visible' => -1, 'position' => 130),
365
        'fk_accountancy_journal' => array('type' => 'integer', 'label' => 'Accountancy journal ID', 'enabled' => 1, 'visible' => -1, 'position' => 132),
366
        'accountancy_journal' => array('type' => 'varchar(20)', 'label' => 'Accountancy journal', 'enabled' => 1, 'visible' => -1, 'position' => 135),
367
        'currency_code' => array('type' => 'varchar(3)', 'label' => 'Currency code', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'position' => 140),
368
        'min_allowed' => array('type' => 'integer', 'label' => 'Min allowed', 'enabled' => 1, 'visible' => -1, 'position' => 145),
369
        'min_desired' => array('type' => 'integer', 'label' => 'Min desired', 'enabled' => 1, 'visible' => -1, 'position' => 150),
370
        'comment' => array('type' => 'text', 'label' => 'Comment', 'enabled' => 1, 'visible' => -1, 'position' => 155),
371
        'datec' => array('type' => 'datetime', 'label' => 'DateCreation', 'enabled' => 1, 'visible' => -1, 'position' => 156),
372
        'tms' => array('type' => 'timestamp', 'label' => 'DateModification', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'position' => 157),
373
        'fk_user_author' => array('type' => 'integer:User:user/class/user.class.php', 'label' => 'Fk user author', 'enabled' => 1, 'visible' => -1, 'position' => 160),
374
        'fk_user_modif' => array('type' => 'integer:User:user/class/user.class.php', 'label' => 'UserModif', 'enabled' => 1, 'visible' => -2, 'notnull' => -1, 'position' => 165),
375
        'note_public' => array('type' => 'html', 'label' => 'NotePublic', 'enabled' => 1, 'visible' => 0, 'position' => 170),
376
        'model_pdf' => array('type' => 'varchar(255)', 'label' => 'Model pdf', 'enabled' => 1, 'visible' => 0, 'position' => 175),
377
        'import_key' => array('type' => 'varchar(14)', 'label' => 'ImportId', 'enabled' => 1, 'visible' => -2, 'position' => 180),
378
        'extraparams' => array('type' => 'varchar(255)', 'label' => 'Extraparams', 'enabled' => 1, 'visible' => -1, 'position' => 185),
379
    );
380
    // END MODULEBUILDER PROPERTIES
381
382
    /**
383
     * Current account
384
     */
385
    const TYPE_CURRENT = 1;
386
    /**
387
     * Cash account
388
     */
389
    const TYPE_CASH = 2;
390
    /**
391
     * Savings account
392
     */
393
    const TYPE_SAVINGS = 0;
394
395
396
    const STATUS_OPEN = 0;
397
    const STATUS_CLOSED = 1;
398
399
400
    /**
401
     * Provide list of deprecated properties and replacements
402
     *
403
     * @return array<string,string>  Old property to new property mapping
404
     */
405
    protected function deprecatedProperties()
406
    {
407
        return array(
408
            'proprio' => 'owner_name',
409
            'domiciliation' => 'owner_address',
410
            'courant' => 'type',
411
            'clos' => 'status',
412
            'solde' => 'balance',
413
        ) + parent::deprecatedProperties();
414
    }
415
416
    /**
417
     *  Constructor
418
     *
419
     *  @param  DoliDB      $db     Database handler
420
     */
421
    public function __construct(DoliDB $db)
422
    {
423
        global $langs;
424
425
        $this->db = $db;
426
427
        $this->ismultientitymanaged = 1;
428
429
        $this->balance = 0;
430
431
        $this->type_lib = array(
432
            self::TYPE_SAVINGS => $langs->transnoentitiesnoconv("BankType0"),
433
            self::TYPE_CURRENT => $langs->transnoentitiesnoconv("BankType1"),
434
            self::TYPE_CASH => $langs->transnoentitiesnoconv("BankType2"),
435
        );
436
437
        $this->labelStatus = array(
438
            self::STATUS_OPEN => $langs->transnoentitiesnoconv("StatusAccountOpened"),
439
            self::STATUS_CLOSED => $langs->transnoentitiesnoconv("StatusAccountClosed")
440
        );
441
    }
442
443
    /**
444
     * Shows the account number in the appropriate format
445
     *
446
     * @return string
447
     */
448
    public function __toString()
449
    {
450
        $string = '';
451
        foreach ($this->getFieldsToShow() as $val) {
452
            if ($val == 'BankCode') {
453
                $string .= $this->code_banque . ' ';
454
            } elseif ($val == 'BankAccountNumber') {
455
                $string .= $this->number . ' ';
456
            } elseif ($val == 'DeskCode') {
457
                $string .= $this->code_guichet . ' ';
458
            } elseif ($val == 'BankAccountNumberKey') {
459
                $string .= $this->cle_rib . ' ';
460
            } elseif ($val == 'BIC') {
461
                $string .= $this->bic . ' ';
462
            } elseif ($val == 'IBAN') {
463
                $string .= $this->iban . ' ';
464
            }
465
        }
466
467
        return trim($string);
468
    }
469
470
471
    /**
472
     *  Return if a bank account need to be conciliated
473
     *
474
     *  @return     int         1 if need to be concialiated, < 0 otherwise.
475
     */
476
    public function canBeConciliated()
477
    {
478
        global $conf;
479
480
        if (empty($this->rappro)) {
481
            return -1;
482
        }
483
        if ($this->type == Account::TYPE_CASH && !getDolGlobalString('BANK_CAN_RECONCILIATE_CASHACCOUNT')) {
484
            return -2;
485
        }
486
        if ($this->status) {
487
            return -3;
488
        }
489
        return 1;
490
    }
491
492
493
	// phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
494
    /**
495
     *      Add a link between bank line record and its source
496
     *
497
     *      @param  int     $line_id    Id of bank entry
498
     *      @param  int     $url_id     Id of object related to link
499
     *      @param  string  $url        Url (deprecated, we use now 'url_id' and 'type' instead)
500
     *      @param  string  $label      Link label
501
     *      @param  string  $type       Type of link ('payment', 'company', 'member', ...)
502
     *      @return int                 Return integer <0 if KO, id line if OK
503
     */
504
    public function add_url_line($line_id, $url_id, $url, $label, $type)
505
    {
506
		// phpcs:enable
507
        $sql = "INSERT INTO " . MAIN_DB_PREFIX . "bank_url (";
508
        $sql .= "fk_bank";
509
        $sql .= ", url_id";
510
        $sql .= ", url";        // deprecated
511
        $sql .= ", label";
512
        $sql .= ", type";
513
        $sql .= ") VALUES (";
514
        $sql .= ((int) $line_id);
515
        $sql .= ", " . ((int) $url_id);
516
        $sql .= ", '" . $this->db->escape($url) . "'";      // deprecated
517
        $sql .= ", '" . $this->db->escape($label) . "'";
518
        $sql .= ", '" . $this->db->escape($type) . "'";
519
        $sql .= ")";
520
521
        dol_syslog(get_class($this) . "::add_url_line", LOG_DEBUG);
522
        if ($this->db->query($sql)) {
523
            $rowid = $this->db->last_insert_id(MAIN_DB_PREFIX . "bank_url");
524
            return $rowid;
525
        } else {
526
            $this->error = $this->db->lasterror();
527
            return -1;
528
        }
529
    }
530
531
	// phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
532
    /**
533
     *      TODO Move this into AccountLine
534
     *      Return array with links from llx_bank_url
535
     *
536
     *      @param  int         $fk_bank    To search using bank transaction id
537
     *      @param  int         $url_id     To search using link to
538
     *      @param  string      $type       To search using type
539
     *      @return array|int               Array of links array('url'=>, 'url_id'=>, 'label'=>, 'type'=> 'fk_bank'=> ) or -1 on error
540
     */
541
    public function get_url($fk_bank = 0, $url_id = 0, $type = '')
542
    {
543
		// phpcs:enable
544
        $lines = array();
545
546
        // Check parameters
547
        if (!empty($fk_bank) && (!empty($url_id) || !empty($type))) {
548
            $this->error = "ErrorBadParameter";
549
            return -1;
550
        }
551
552
        $sql = "SELECT fk_bank, url_id, url, label, type";
553
        $sql .= " FROM " . MAIN_DB_PREFIX . "bank_url";
554
        if ($fk_bank > 0) {
555
            $sql .= " WHERE fk_bank = " . ((int) $fk_bank);
556
        } else {
557
            $sql .= " WHERE url_id = " . ((int) $url_id) . " AND type = '" . $this->db->escape($type) . "'";
558
        }
559
        $sql .= " ORDER BY type, label";
560
561
        dol_syslog(get_class($this) . "::get_url", LOG_DEBUG);
562
        $result = $this->db->query($sql);
563
        if ($result) {
564
            $i = 0;
565
            $num = $this->db->num_rows($result);
566
            while ($i < $num) {
567
                $obj = $this->db->fetch_object($result);
568
                // Anciens liens (pour compatibilite)
569
                $lines[$i][0] = $obj->url;
570
                $lines[$i][1] = $obj->url_id;
571
                $lines[$i][2] = $obj->label;
572
                $lines[$i][3] = $obj->type;
573
                // Nouveaux liens
574
                $lines[$i]['url'] = $obj->url;
575
                $lines[$i]['url_id'] = $obj->url_id;
576
                $lines[$i]['label'] = $obj->label;
577
                $lines[$i]['type'] = $obj->type;
578
                $lines[$i]['fk_bank'] = $obj->fk_bank;
579
                $i++;
580
            }
581
        } else {
582
            dol_print_error($this->db);
583
        }
584
585
        return $lines;
586
    }
587
588
    /**
589
     *  Add an entry into table ".MAIN_DB_PREFIX."bank
590
     *
591
     *  @param  int         $date           Date operation
592
     *  @param  string      $oper           'VIR','PRE','LIQ','VAD','CB','CHQ'...
593
     *  @param  string      $label          Description
594
     *  @param  float       $amount         Amount
595
     *  @param  string      $num_chq        Numero cheque or transfer
596
     *  @param  int         $categorie      Category id (optional)
597
     *  @param  User        $user           User that create
598
     *  @param  string      $emetteur       Name of cheque writer
599
     *  @param  string      $banque         Bank of cheque writer
600
     *  @param  string      $accountancycode    When we record a free bank entry, we must provide accounting account if accountancy module is on.
601
     *  @param  int         $datev          Date value
602
     *  @param  string      $num_releve     Label of bank receipt for reconciliation
603
     *  @param  float       $amount_main_currency   Amount
604
     *  @return int                         Rowid of added entry, <0 if KO
605
     */
606
    public function addline($date, $oper, $label, $amount, $num_chq, $categorie, User $user, $emetteur = '', $banque = '', $accountancycode = '', $datev = null, $num_releve = '', $amount_main_currency = null)
607
    {
608
        global $langs;
609
610
        // Deprecation warning
611
        if (is_numeric($oper)) {
612
            dol_syslog(__METHOD__ . ": using numeric operations is deprecated", LOG_WARNING);
613
        }
614
615
        if (empty($this->id) && !empty($this->rowid)) { // For backward compatibility
616
            $this->id = $this->rowid;
617
        }
618
619
        // Clean parameters
620
        $emetteur = trim($emetteur);
621
        $banque = trim($banque);
622
        $label = trim($label);
623
624
        $now = dol_now();
625
626
        if (is_numeric($oper)) {    // Clean operation to have a code instead of a rowid
627
            $sql = "SELECT code FROM " . MAIN_DB_PREFIX . "c_paiement";
628
            $sql .= " WHERE id = " . ((int) $oper);
629
            $sql .= " AND entity IN (" . getEntity('c_paiement') . ")";
630
            $resql = $this->db->query($sql);
631
            if ($resql) {
632
                $obj = $this->db->fetch_object($resql);
633
                $oper = $obj->code;
634
            } else {
635
                dol_print_error($this->db, 'Failed to get payment type code');
636
                return -1;
637
            }
638
        }
639
640
        // Check parameters
641
        if (!$oper) {
642
            $this->error = $langs->trans("OperNotDefined");
643
            return -1;
644
        }
645
        if (!$this->id) {
646
            $this->error = $langs->trans("ThisIdNotDefined");
647
            return -2;
648
        }
649
        if ($this->type == Account::TYPE_CASH && $oper != 'LIQ') {
650
            $this->error = "ErrorCashAccountAcceptsOnlyCashMoney";
651
            return -3;
652
        }
653
654
        $this->db->begin();
655
656
        if (is_null($datev) || empty($datev)) {
657
            $datev = $date;
658
        }
659
660
        $accline = new AccountLine($this->db);
661
        $accline->datec = $now;
662
        $accline->dateo = $date;
663
        $accline->datev = $datev;
664
        $accline->label = $label;
665
        $accline->amount = $amount;
666
        $accline->amount_main_currency = $amount_main_currency;
667
        $accline->fk_user_author = $user->id;
668
        $accline->fk_account = $this->id;
669
        $accline->fk_type = $oper;
670
        $accline->numero_compte = $accountancycode;
671
        $accline->num_releve = $num_releve;
672
673
        if ($num_chq) {
674
            $accline->num_chq = $num_chq;
675
        }
676
677
        if ($emetteur) {
678
            $accline->emetteur = $emetteur;
679
        }
680
681
        if ($banque) {
682
            $accline->bank_chq = $banque;
683
        }
684
685
        if ($accline->insert() > 0) {
686
            if ($categorie > 0) {
687
                $sql = "INSERT INTO " . MAIN_DB_PREFIX . "bank_class(";
688
                $sql .= "lineid, fk_categ";
689
                $sql .= ") VALUES (";
690
                $sql .= ((int) $accline->id) . ", '" . $this->db->escape($categorie) . "'";
691
                $sql .= ")";
692
693
                $result = $this->db->query($sql);
694
                if (!$result) {
695
                    $this->error = $this->db->lasterror();
696
                    $this->db->rollback();
697
698
                    return -4;
699
                }
700
            }
701
702
            $this->db->commit();
703
704
            return $accline->id;
705
        } else {
706
            $this->setErrorsFromObject($accline);
707
            $this->db->rollback();
708
709
            return -5;
710
        }
711
    }
712
713
    /**
714
     *  Create bank account into database
715
     *
716
     *  @param  User    $user       Object user making creation
717
     *  @param  int     $notrigger  1=Disable triggers
718
     *  @return int                 Return integer < 0 if KO, > 0 if OK
719
     */
720
    public function create(User $user, $notrigger = 0)
721
    {
722
        global $langs, $conf;
723
724
        $error = 0;
725
726
        // Clean parameters
727
        if (!$this->min_allowed) {
728
            $this->min_allowed = 0;
729
        }
730
        if (!$this->min_desired) {
731
            $this->min_desired = 0;
732
        }
733
734
        // Check parameters
735
        if (empty($this->country_id)) {
736
            $this->error = $langs->transnoentitiesnoconv("ErrorFieldRequired", $langs->transnoentitiesnoconv("Country"));
737
            dol_syslog(get_class($this) . "::create " . $this->error, LOG_ERR);
738
            return -1;
739
        }
740
        if (empty($this->ref)) {
741
            $this->error = $langs->transnoentitiesnoconv("ErrorFieldRequired", $langs->transnoentitiesnoconv("Ref"));
742
            dol_syslog(get_class($this) . "::create " . $this->error, LOG_ERR);
743
            return -1;
744
        }
745
        if (empty($this->date_solde)) {
746
            $this->error = $langs->transnoentitiesnoconv("ErrorFieldRequired", $langs->transnoentitiesnoconv("DateInitialBalance"));
747
            dol_syslog(get_class($this) . "::create " . $this->error, LOG_ERR);
748
            return -1;
749
        }
750
751
        // Load libraries to check BAN
752
        $balance = $this->balance;
753
        if (empty($balance) && !empty($this->solde)) {
754
            $balance = $this->solde;
755
        }
756
        if (empty($balance)) {
757
            $balance = 0;
758
        }
759
        if (empty($this->address && !empty($this->domiciliation))) {
760
            dol_syslog(get_class($this) . "::create domiciliation is deprecated use address", LOG_NOTICE);
761
            $this->address = $this->domiciliation;
762
        }
763
        if (empty($this->status && !empty($this->clos))) {
0 ignored issues
show
Deprecated Code introduced by
The property Dolibarr\Code\Compta\Classes\Account::$clos has been deprecated: Duplicate field. We already have the field $this->status ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

763
        if (empty($this->status && !empty(/** @scrutinizer ignore-deprecated */ $this->clos))) {

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
764
            dol_syslog(get_class($this) . "::create clos is deprecated use status", LOG_NOTICE);
765
            $this->status = $this->clos;
0 ignored issues
show
Deprecated Code introduced by
The property Dolibarr\Code\Compta\Classes\Account::$clos has been deprecated: Duplicate field. We already have the field $this->status ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

765
            $this->status = /** @scrutinizer ignore-deprecated */ $this->clos;

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
766
        }
767
768
        // Load the library to validate/check a BAN account
769
        require_once constant('DOL_DOCUMENT_ROOT') . '/core/lib/bank.lib.php';
770
771
        $now = dol_now();
772
773
        $this->db->begin();
774
775
        $sql = "INSERT INTO " . MAIN_DB_PREFIX . "bank_account (";
776
        $sql .= "datec";
777
        $sql .= ", ref";
778
        $sql .= ", label";
779
        $sql .= ", entity";
780
        $sql .= ", account_number";
781
        $sql .= ", fk_accountancy_journal";
782
        $sql .= ", bank";
783
        $sql .= ", code_banque";
784
        $sql .= ", code_guichet";
785
        $sql .= ", number";
786
        $sql .= ", cle_rib";
787
        $sql .= ", bic";
788
        $sql .= ", iban_prefix";
789
        $sql .= ", domiciliation";
790
        $sql .= ", pti_in_ctti";
791
        $sql .= ", proprio";
792
        $sql .= ", owner_address";
793
        $sql .= ", owner_zip";
794
        $sql .= ", owner_town";
795
        $sql .= ", owner_country_id";
796
        $sql .= ", currency_code";
797
        $sql .= ", rappro";
798
        $sql .= ", min_allowed";
799
        $sql .= ", min_desired";
800
        $sql .= ", comment";
801
        $sql .= ", state_id";
802
        $sql .= ", fk_pays";
803
        $sql .= ", ics";
804
        $sql .= ", ics_transfer";
805
        $sql .= ") VALUES (";
806
        $sql .= "'" . $this->db->idate($now) . "'";
807
        $sql .= ", '" . $this->db->escape($this->ref) . "'";
808
        $sql .= ", '" . $this->db->escape($this->label) . "'";
809
        $sql .= ", " . ((int) $conf->entity);
810
        $sql .= ", '" . $this->db->escape($this->account_number) . "'";
811
        $sql .= ", " . ($this->fk_accountancy_journal > 0 ? ((int) $this->fk_accountancy_journal) : "null");
812
        $sql .= ", '" . $this->db->escape($this->bank) . "'";
813
        $sql .= ", '" . $this->db->escape($this->code_banque) . "'";
814
        $sql .= ", '" . $this->db->escape($this->code_guichet) . "'";
815
        $sql .= ", '" . $this->db->escape($this->number) . "'";
816
        $sql .= ", '" . $this->db->escape($this->cle_rib) . "'";
817
        $sql .= ", '" . $this->db->escape($this->bic) . "'";
818
        $sql .= ", '" . $this->db->escape($this->iban) . "'";
819
        $sql .= ", '" . $this->db->escape($this->address) . "'";
820
        $sql .= ", " . ((int) $this->pti_in_ctti);
821
        $sql .= ", '" . $this->db->escape($this->proprio) . "'";
822
        $sql .= ", '" . $this->db->escape($this->owner_address) . "'";
823
        $sql .= ", '" . $this->db->escape($this->owner_zip) . "'";
824
        $sql .= ", '" . $this->db->escape($this->owner_town) . "'";
825
        $sql .= ", " . ($this->owner_country_id > 0 ? ((int) $this->owner_country_id) : "null");
826
        $sql .= ", '" . $this->db->escape($this->currency_code) . "'";
827
        $sql .= ", " . ((int) $this->rappro);
828
        $sql .= ", " . price2num($this->min_allowed, 'MT');
829
        $sql .= ", " . price2num($this->min_desired, 'MT');
830
        $sql .= ", '" . $this->db->escape($this->comment) . "'";
831
        $sql .= ", " . ($this->state_id > 0 ? ((int) $this->state_id) : "null");
832
        $sql .= ", " . ($this->country_id > 0 ? ((int) $this->country_id) : "null");
833
        $sql .= ", '" . $this->db->escape($this->ics) . "'";
834
        $sql .= ", '" . $this->db->escape($this->ics_transfer) . "'";
835
        $sql .= ")";
836
837
        dol_syslog(get_class($this) . "::create", LOG_DEBUG);
838
        $resql = $this->db->query($sql);
839
        if ($resql) {
840
            $this->id = $this->db->last_insert_id(MAIN_DB_PREFIX . "bank_account");
841
842
            $result = $this->update($user, 1);
843
            if ($result > 0) {
844
                $accline = new AccountLine($this->db);
845
                $accline->datec = $now;
846
                $accline->label = '(' . $langs->trans("InitialBankBalance") . ')';
847
                $accline->amount = (float) price2num($balance);
848
                $accline->fk_user_author = $user->id;
849
                $accline->fk_account = $this->id;
850
                $accline->datev = $this->date_solde;
851
                $accline->dateo = $this->date_solde;
852
                $accline->fk_type = 'SOLD';
853
854
                if ($accline->insert() < 0) {
855
                    $error++;
856
                    $this->error = $accline->error;
857
                    $this->errors = $accline->errors;
858
                }
859
860
                if (!$error) {
861
                    $result = $this->insertExtraFields();
862
                    if ($result < 0) {
863
                        $error++;
864
                    }
865
                }
866
867
                if (!$error && !$notrigger) {
868
                    // Call trigger
869
                    $result = $this->call_trigger('BANKACCOUNT_CREATE', $user);
870
                    if ($result < 0) {
871
                        $error++;
872
                    }
873
                    // End call triggers
874
                }
875
            } else {
876
                $error++;
877
            }
878
        } else {
879
            if ($this->db->errno() == 'DB_ERROR_RECORD_ALREADY_EXISTS') {
880
                $this->error = $langs->trans("ErrorBankLabelAlreadyExists");
881
                $error++;
882
            } else {
883
                $this->error = $this->db->error() . " sql=" . $sql;
884
                $error++;
885
            }
886
        }
887
888
        if (!$error) {
889
            $this->db->commit();
890
            return $this->id;
891
        } else {
892
            $this->db->rollback();
893
            return -1 * $error;
894
        }
895
    }
896
897
    /**
898
     *      Update bank account card
899
     *
900
     *      @param  User    $user       Object user making action
901
     *      @param  int     $notrigger  1=Disable triggers
902
     *      @return int                 Return integer <0 if KO, >0 if OK
903
     */
904
    public function update(User $user, $notrigger = 0)
905
    {
906
        global $langs;
907
908
        $error = 0;
909
910
        $this->db->begin();
911
912
        // Check parameters
913
        if (empty($this->country_id)) {
914
            $this->error = $langs->transnoentitiesnoconv("ErrorFieldRequired", $langs->transnoentitiesnoconv("Country"));
915
            dol_syslog(get_class($this) . "::update " . $this->error, LOG_ERR);
916
            return -1;
917
        }
918
        if (empty($this->ref)) {
919
            $this->error = $langs->transnoentitiesnoconv("ErrorFieldRequired", $langs->transnoentitiesnoconv("Ref"));
920
            dol_syslog(get_class($this) . "::update " . $this->error, LOG_ERR);
921
            return -1;
922
        }
923
        if (!$this->label) {
924
            $this->label = "???";
925
        }
926
927
        $sql = "UPDATE " . MAIN_DB_PREFIX . "bank_account SET ";
928
929
        $sql .= " ref   = '" . $this->db->escape($this->ref) . "'";
930
        $sql .= ",label = '" . $this->db->escape($this->label) . "'";
931
932
        $sql .= ",courant = " . ((int) $this->type);
933
        $sql .= ",clos = " . ((int) $this->status);
934
        $sql .= ",rappro = " . ((int) $this->rappro);
935
        $sql .= ",url = " . ($this->url ? "'" . $this->db->escape($this->url) . "'" : "null");
936
        $sql .= ",account_number = '" . $this->db->escape($this->account_number) . "'";
937
        $sql .= ",fk_accountancy_journal = " . ($this->fk_accountancy_journal > 0 ? ((int) $this->fk_accountancy_journal) : "null");
938
        $sql .= ",bank  = '" . $this->db->escape($this->bank) . "'";
939
        $sql .= ",code_banque='" . $this->db->escape($this->code_banque) . "'";
940
        $sql .= ",code_guichet='" . $this->db->escape($this->code_guichet) . "'";
941
        $sql .= ",number='" . $this->db->escape($this->number) . "'";
942
        $sql .= ",cle_rib='" . $this->db->escape($this->cle_rib) . "'";
943
        $sql .= ",bic='" . $this->db->escape($this->bic) . "'";
944
        $sql .= ",iban_prefix = '" . $this->db->escape($this->iban) . "'";
945
        $sql .= ",domiciliation='" . $this->db->escape($this->address) . "'";
946
        $sql .= ",pti_in_ctti=" . ((int) $this->pti_in_ctti);
947
        $sql .= ",proprio = '" . $this->db->escape($this->proprio) . "'";
948
        $sql .= ",owner_address = '" . $this->db->escape($this->owner_address) . "'";
949
        $sql .= ",owner_zip = '" . $this->db->escape($this->owner_zip) . "'";
950
        $sql .= ",owner_town = '" . $this->db->escape($this->owner_town) . "'";
951
        $sql .= ",owner_country_id = " . ($this->owner_country_id > 0 ? ((int) $this->owner_country_id) : "null");
952
953
        $sql .= ",currency_code = '" . $this->db->escape($this->currency_code) . "'";
954
955
        $sql .= ",min_allowed = " . ($this->min_allowed != '' ? price2num($this->min_allowed) : "null");
956
        $sql .= ",min_desired = " . ($this->min_desired != '' ? price2num($this->min_desired) : "null");
957
        $sql .= ",comment = '" . $this->db->escape($this->comment) . "'";
958
959
        $sql .= ",state_id = " . ($this->state_id > 0 ? ((int) $this->state_id) : "null");
960
        $sql .= ",fk_pays = " . ($this->country_id > 0 ? ((int) $this->country_id) : "null");
961
        $sql .= ",ics = '" . $this->db->escape($this->ics) . "'";
962
        $sql .= ",ics_transfer = '" . $this->db->escape($this->ics_transfer) . "'";
963
964
        $sql .= " WHERE rowid = " . ((int) $this->id);
965
966
        dol_syslog(get_class($this) . "::update", LOG_DEBUG);
967
        $result = $this->db->query($sql);
968
        if ($result) {
969
            // Actions on extra fields (by external module or standard code)
970
            if (!$error) {
971
                $result = $this->insertExtraFields();
972
                if ($result < 0) {
973
                    $error++;
974
                }
975
            }
976
977
            if (!$error && !$notrigger) {
978
                // Call trigger
979
                $result = $this->call_trigger('BANKACCOUNT_MODIFY', $user);
980
                if ($result < 0) {
981
                    $error++;
982
                }
983
                // End call triggers
984
            }
985
        } else {
986
            $error++;
987
            $this->error = $this->db->lasterror();
988
            dol_print_error($this->db);
989
        }
990
991
        if (!$error) {
992
            $this->db->commit();
993
            return $this->id;
994
        } else {
995
            $this->db->rollback();
996
            return -1 * $error;
997
        }
998
    }
999
1000
1001
	// phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
1002
    /**
1003
     *  Update BBAN (RIB) account fields
1004
     *
1005
     *  @param  User|null   $user       Object user making update
1006
     *  @return int                     Return integer <0 if KO, >0 if OK
1007
     */
1008
    public function update_bban(User $user = null)
1009
    {
1010
		// phpcs:enable
1011
        global $conf, $langs;
1012
1013
        // Load library to get BAN control function
1014
        require_once constant('DOL_DOCUMENT_ROOT') . '/core/lib/bank.lib.php';
1015
1016
        dol_syslog(get_class($this) . "::update_bban $this->code_banque,$this->code_guichet,$this->number,$this->cle_rib,$this->iban");
1017
1018
        // Check parameters
1019
        if (!$this->ref) {
1020
            $this->error = $langs->transnoentitiesnoconv("ErrorFieldRequired", $langs->trans("Ref"));
1021
            return -2;
1022
        }
1023
1024
        $sql = "UPDATE " . MAIN_DB_PREFIX . "bank_account SET ";
1025
        $sql .= " bank  = '" . $this->db->escape($this->bank) . "'";
1026
        $sql .= ",code_banque='" . $this->db->escape($this->code_banque) . "'";
1027
        $sql .= ",code_guichet='" . $this->db->escape($this->code_guichet) . "'";
1028
        $sql .= ",number='" . $this->db->escape($this->number) . "'";
1029
        $sql .= ",cle_rib='" . $this->db->escape($this->cle_rib) . "'";
1030
        $sql .= ",bic='" . $this->db->escape($this->bic) . "'";
1031
        $sql .= ",iban_prefix = '" . $this->db->escape($this->iban) . "'";
1032
        $sql .= ",domiciliation='" . $this->db->escape($this->domiciliation) . "'";
1033
        $sql .= ",proprio = '" . $this->db->escape($this->proprio) . "'";
1034
        $sql .= ",owner_address = '" . $this->db->escape($this->owner_address) . "'";
1035
        $sql .= ",owner_zip = '" . $this->db->escape($this->owner_zip) . "'";
1036
        $sql .= ",owner_town = '" . $this->db->escape($this->owner_town) . "'";
1037
        $sql .= ",owner_country_id = " . ($this->owner_country_id > 0 ? ((int) $this->owner_country_id) : "null");
1038
        $sql .= ",state_id = " . ($this->state_id > 0 ? $this->state_id : "null");
1039
        $sql .= ",fk_pays = " . ($this->country_id > 0 ? $this->country_id : "null");
1040
        $sql .= " WHERE rowid = " . ((int) $this->id);
1041
        $sql .= " AND entity = " . ((int) $conf->entity);
1042
1043
        dol_syslog(get_class($this) . "::update_bban", LOG_DEBUG);
1044
1045
        $result = $this->db->query($sql);
1046
        if ($result) {
1047
            return 1;
1048
        } else {
1049
            $this->error = $this->db->lasterror();
1050
            dol_print_error($this->db);
1051
            return -1;
1052
        }
1053
    }
1054
1055
1056
    /**
1057
     *      Load a bank account into memory from database
1058
     *
1059
     *      @param  int     $id         Id of bank account to get
1060
     *      @param  string  $ref        Ref of bank account to get
1061
     *      @return int                 Return integer <0 if KO, >0 if OK
1062
     */
1063
    public function fetch($id, $ref = '')
1064
    {
1065
        if (empty($id) && empty($ref)) {
1066
            $this->error = "ErrorBadParameters";
1067
            return -1;
1068
        }
1069
1070
        $sql = "SELECT ba.rowid, ba.ref, ba.label, ba.bank, ba.number, ba.courant as type, ba.clos as status, ba.rappro, ba.url,";
1071
        $sql .= " ba.code_banque, ba.code_guichet, ba.cle_rib, ba.bic, ba.iban_prefix as iban,";
1072
        $sql .= " ba.domiciliation as address, ba.pti_in_ctti, ba.proprio as owner_name, ba.owner_address, ba.owner_zip, ba.owner_town, ba.owner_country_id, ba.state_id, ba.fk_pays as country_id,";
1073
        $sql .= " ba.account_number, ba.fk_accountancy_journal, ba.currency_code,";
1074
        $sql .= " ba.min_allowed, ba.min_desired, ba.comment,";
1075
        $sql .= " ba.datec as date_creation, ba.tms as date_modification, ba.ics, ba.ics_transfer,";
1076
        $sql .= ' c.code as country_code, c.label as country,';
1077
        $sql .= ' d.code_departement as state_code, d.nom as state,';
1078
        $sql .= ' aj.code as accountancy_journal';
1079
        $sql .= " FROM " . MAIN_DB_PREFIX . "bank_account as ba";
1080
        $sql .= ' LEFT JOIN ' . MAIN_DB_PREFIX . 'c_country as c ON ba.fk_pays = c.rowid';
1081
        $sql .= ' LEFT JOIN ' . MAIN_DB_PREFIX . 'c_departements as d ON ba.state_id = d.rowid';
1082
        $sql .= ' LEFT JOIN ' . MAIN_DB_PREFIX . 'accounting_journal as aj ON aj.rowid=ba.fk_accountancy_journal';
1083
        $sql .= " WHERE ba.entity IN (" . getEntity($this->element) . ")";
1084
        if ($id) {
1085
            $sql .= " AND ba.rowid = " . ((int) $id);
1086
        }
1087
        if ($ref) {
1088
            $sql .= " AND ba.ref = '" . $this->db->escape($ref) . "'";
1089
        }
1090
1091
        dol_syslog(get_class($this) . "::fetch", LOG_DEBUG);
1092
        $result = $this->db->query($sql);
1093
        if ($result) {
1094
            if ($this->db->num_rows($result)) {
1095
                $obj = $this->db->fetch_object($result);
1096
1097
                $this->id            = $obj->rowid;
1098
                $this->rowid         = $obj->rowid;
1099
                $this->ref           = $obj->ref;
1100
                $this->label         = $obj->label;
1101
                $this->type          = $obj->type;
1102
                $this->courant       = $obj->type;
1103
                $this->bank          = $obj->bank;
1104
                $this->clos          = $obj->status;
0 ignored issues
show
Deprecated Code introduced by
The property Dolibarr\Code\Compta\Classes\Account::$clos has been deprecated: Duplicate field. We already have the field $this->status ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

1104
                /** @scrutinizer ignore-deprecated */ $this->clos          = $obj->status;

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
1105
                $this->status = $obj->status;
1106
                $this->rappro        = $obj->rappro;
1107
                $this->url           = $obj->url;
1108
1109
                $this->code_banque   = $obj->code_banque;
1110
                $this->code_guichet  = $obj->code_guichet;
1111
                $this->number        = $obj->number;
1112
                $this->cle_rib       = $obj->cle_rib;
1113
                $this->bic           = $obj->bic;
1114
                $this->iban          = $obj->iban;
1115
                $this->domiciliation = $obj->address;
1116
                $this->address       = $obj->address;
1117
                $this->pti_in_ctti   = $obj->pti_in_ctti;
1118
                $this->proprio = $obj->owner_name;
1119
                $this->owner_name = $obj->owner_name;
1120
                $this->owner_address = $obj->owner_address;
1121
                $this->owner_zip     = $obj->owner_zip;
1122
                $this->owner_town    = $obj->owner_town;
1123
                $this->owner_country_id = $obj->owner_country_id;
1124
1125
                $this->state_id        = $obj->state_id;
1126
                $this->state_code      = $obj->state_code;
1127
                $this->state           = $obj->state;
1128
1129
                $this->country_id    = $obj->country_id;
1130
                $this->country_code  = $obj->country_code;
1131
                $this->country       = $obj->country;
1132
1133
                $this->account_number = $obj->account_number;
1134
                $this->fk_accountancy_journal = $obj->fk_accountancy_journal;
1135
                $this->accountancy_journal = $obj->accountancy_journal;
1136
1137
                $this->currency_code  = $obj->currency_code;
1138
                $this->account_currency_code = $obj->currency_code;
0 ignored issues
show
Deprecated Code introduced by
The property Dolibarr\Code\Compta\Cla...:$account_currency_code has been deprecated: Use currency_code instead ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

1138
                /** @scrutinizer ignore-deprecated */ $this->account_currency_code = $obj->currency_code;

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
1139
                $this->min_allowed    = $obj->min_allowed;
1140
                $this->min_desired    = $obj->min_desired;
1141
                $this->comment        = $obj->comment;
1142
1143
                $this->date_creation  = $this->db->jdate($obj->date_creation);
1144
                $this->date_modification = $this->db->jdate($obj->date_modification);
1145
1146
                $this->ics           = $obj->ics;
1147
                $this->ics_transfer  = $obj->ics_transfer;
1148
1149
                // Retrieve all extrafield
1150
                // fetch optionals attributes and labels
1151
                $this->fetch_optionals();
1152
1153
                return 1;
1154
            } else {
1155
                return 0;
1156
            }
1157
        } else {
1158
            $this->error = $this->db->lasterror();
1159
            $this->errors[] = $this->error;
1160
            return -1;
1161
        }
1162
    }
1163
1164
    /**
1165
     * Sets object to supplied categories.
1166
     *
1167
     * Deletes object from existing categories not supplied.
1168
     * Adds it to non existing supplied categories.
1169
     * Existing categories are left untouch.
1170
     *
1171
     * @param   int[]|int   $categories     Category or categories IDs
1172
     * @return  int                         Return integer <0 if KO, >0 if OK
1173
     */
1174
    public function setCategories($categories)
1175
    {
1176
        return parent::setCategoriesCommon($categories, Categorie::TYPE_ACCOUNT);
1177
    }
1178
1179
    /**
1180
     *  Delete bank account from database
1181
     *
1182
     *  @param  User|null   $user       User deleting
1183
     *  @param  int         $notrigger  1=Disable triggers
1184
     *  @return int                     Return integer <0 if KO, >0 if OK
1185
     */
1186
    public function delete(User $user = null, $notrigger = 0)
1187
    {
1188
        $error = 0;
1189
1190
        $this->db->begin();
1191
1192
        // @TODO Check there is no child into llx_payment_various, ... to allow deletion ?
1193
1194
        // Delete link between tag and bank account
1195
        if (!$error) {
1196
            $sql = "DELETE FROM " . MAIN_DB_PREFIX . "categorie_account";
1197
            $sql .= " WHERE fk_account = " . ((int) $this->id);
1198
1199
            $resql = $this->db->query($sql);
1200
            if (!$resql) {
1201
                $error++;
1202
                $this->error = "Error " . $this->db->lasterror();
1203
            }
1204
        }
1205
1206
        if (!$error) {
1207
            $sql = "DELETE FROM " . MAIN_DB_PREFIX . $this->table_element;
1208
            $sql .= " WHERE rowid = " . ((int) $this->id);
1209
1210
            dol_syslog(get_class($this) . "::delete", LOG_DEBUG);
1211
            $result = $this->db->query($sql);
1212
            if ($result) {
1213
                // Remove extrafields
1214
                if (!$error) {
1215
                    $result = $this->deleteExtraFields();
1216
                    if ($result < 0) {
1217
                        $error++;
1218
                        dol_syslog(get_class($this) . "::delete error -4 " . $this->error, LOG_ERR);
1219
                    }
1220
                }
1221
            } else {
1222
                $error++;
1223
                $this->error = "Error " . $this->db->lasterror();
1224
            }
1225
        }
1226
1227
        if (!$error) {
1228
            $this->db->commit();
1229
            return 1;
1230
        } else {
1231
            $this->db->rollback();
1232
            return -1;
1233
        }
1234
    }
1235
1236
1237
    /**
1238
     *  Return label of object status
1239
     *
1240
     *  @param      int     $mode           0=long label, 1=short label, 2=Picto + short label, 3=Picto, 4=Picto + long label, 5=short label + picto, 6=Long label + picto
1241
     *  @return     string                  Label
1242
     */
1243
    public function getLibStatut($mode = 0)
1244
    {
1245
        return $this->LibStatut($this->status, $mode);
1246
    }
1247
1248
	// phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
1249
    /**
1250
     *  Return label of given object status
1251
     *
1252
     *  @param   int        $status         Id status
1253
     *  @param   int        $mode           0=long label, 1=short label, 2=Picto + short label, 3=Picto, 4=Picto + long label, 5=short label + picto, 6=Long label + picto
1254
     *  @return  string                     Label
1255
     */
1256
    public function LibStatut($status, $mode = 0)
1257
    {
1258
		// phpcs:enable
1259
        global $langs;
1260
        $langs->load('banks');
1261
1262
        if ($status == self::STATUS_OPEN) {
1263
            $label = $langs->transnoentitiesnoconv("StatusAccountOpened");
1264
            $labelshort = $langs->transnoentitiesnoconv("StatusAccountOpened");
1265
            $statusType = 'status4';
1266
        } else {
1267
            $label = $langs->transnoentitiesnoconv("StatusAccountClosed");
1268
            $labelshort = $langs->transnoentitiesnoconv("StatusAccountClosed");
1269
            $statusType = 'status5';
1270
        }
1271
1272
        return dolGetStatus($label, $labelshort, '', $statusType, $mode);
1273
    }
1274
1275
1276
	// phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
1277
    /**
1278
     *    Indicates if an account can be deleted or not (without movements)
1279
     *
1280
     *    @return     boolean     True is the deletion is ok, false if not
1281
     */
1282
    public function can_be_deleted()
1283
    {
1284
		// phpcs:enable
1285
        $can_be_deleted = false;
1286
1287
        $sql = "SELECT COUNT(rowid) as nb";
1288
        $sql .= " FROM " . MAIN_DB_PREFIX . "bank";
1289
        $sql .= " WHERE fk_account = " . ((int) $this->id);
1290
1291
        $resql = $this->db->query($sql);
1292
        if ($resql) {
1293
            $obj = $this->db->fetch_object($resql);
1294
            if ($obj->nb <= 1) {
1295
                $can_be_deleted = true; // Juste le solde
1296
            }
1297
        } else {
1298
            dol_print_error($this->db);
1299
        }
1300
        return $can_be_deleted;
1301
    }
1302
1303
1304
    /**
1305
     *   Return error
1306
     *
1307
     *   @return    string      Error string
1308
     */
1309
    public function error()
1310
    {
1311
        return $this->error;
1312
    }
1313
1314
    /**
1315
     *  Return current balance
1316
     *
1317
     *  @param  int         $option     1=Exclude future operation date (this is to exclude input made in advance and have real account sold)
1318
     *  @param  int|string              $date_end   Date until we want to get bank account balance
1319
     *  @param  string      $field      'dateo' or 'datev'
1320
     *  @return float|-1                current balance (value date <= today), or -1 if error
0 ignored issues
show
Documentation Bug introduced by
The doc comment float|-1 at position 2 could not be parsed: Unknown type name '-1' at position 2 in float|-1.
Loading history...
1321
     */
1322
    public function solde($option = 0, $date_end = '', $field = 'dateo')
1323
    {
1324
        $solde = 0;
1325
1326
        $sql = "SELECT sum(amount) as amount";
1327
        $sql .= " FROM " . MAIN_DB_PREFIX . "bank";
1328
        $sql .= " WHERE fk_account = " . ((int) $this->id);
1329
        if ($option == 1) {
1330
            $sql .= " AND " . $this->db->escape($field) . " <= '" . (!empty($date_end) ? $this->db->idate($date_end) : $this->db->idate(dol_now())) . "'";
1331
        }
1332
1333
        $resql = $this->db->query($sql);
1334
        if ($resql) {
1335
            if ($this->db->num_rows($resql)) {
1336
                $obj = $this->db->fetch_object($resql);
1337
                $solde = $obj->amount;
1338
            }
1339
            $this->db->free($resql);
1340
        } else {
1341
            $this->errors[] = $this->db->lasterror;
1342
            return -1;
1343
        }
1344
1345
        return (float) price2num($solde, 'MU');
1346
    }
1347
1348
	// phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
1349
    /**
1350
     *      Load indicators for dashboard (this->nbtodo and this->nbtodolate)
1351
     *
1352
     *      @param  User    $user               Object user
1353
     *      @param  int     $filteraccountid    To get info for a particular account id
1354
     *      @return WorkboardResponse|int       Return integer <0 if KO, WorkboardResponse if OK
1355
     */
1356
    public function load_board(User $user, $filteraccountid = 0)
1357
    {
1358
		// phpcs:enable
1359
        global $conf, $langs;
1360
1361
        if ($user->socid) {
1362
            return -1; // protection pour eviter appel par utilisateur externe
1363
        }
1364
1365
        $sql = "SELECT b.rowid, b.datev as datefin";
1366
        $sql .= " FROM " . MAIN_DB_PREFIX . "bank as b,";
1367
        $sql .= " " . MAIN_DB_PREFIX . "bank_account as ba";
1368
        $sql .= " WHERE b.rappro=0";
1369
        $sql .= " AND b.fk_account = ba.rowid";
1370
        $sql .= " AND ba.entity IN (" . getEntity('bank_account') . ")";
1371
        $sql .= " AND (ba.rappro = 1 AND ba.courant != " . Account::TYPE_CASH . ")"; // Compte rapprochable
1372
        $sql .= " AND clos = 0";
1373
        if ($filteraccountid) {
1374
            $sql .= " AND ba.rowid = " . ((int) $filteraccountid);
1375
        }
1376
1377
        $resql = $this->db->query($sql);
1378
        if ($resql) {
1379
            $langs->load("banks");
1380
            $now = dol_now();
1381
1382
1383
            $response = new WorkboardResponse();
1384
            $response->warning_delay = $conf->bank->rappro->warning_delay / 60 / 60 / 24;
1385
            $response->label = $langs->trans("TransactionsToConciliate");
1386
            $response->labelShort = $langs->trans("TransactionsToConciliateShort");
1387
            $response->url = constant('BASE_URL') . '/compta/bank/list.php?leftmenu=bank&amp;mainmenu=bank';
1388
            $response->img = img_object('', "payment");
1389
1390
            while ($obj = $this->db->fetch_object($resql)) {
1391
                $response->nbtodo++;
1392
                if ($this->db->jdate($obj->datefin) < ($now - $conf->bank->rappro->warning_delay)) {
1393
                    $response->nbtodolate++;
1394
                }
1395
            }
1396
1397
            return $response;
1398
        } else {
1399
            dol_print_error($this->db);
1400
            $this->error = $this->db->error();
1401
            return -1;
1402
        }
1403
    }
1404
1405
    /**
1406
     *      Load the indicators this->nb for the state board
1407
     *
1408
     *      @param      int         $filteraccountid    To get info for a particular account id
1409
     *      @return     int         Return integer <0 if KO, >0 if OK
1410
     */
1411
    public function loadStateBoard($filteraccountid = 0)
1412
    {
1413
        global $user;
1414
1415
        if ($user->socid) {
1416
            return -1; // protection pour eviter appel par utilisateur externe
1417
        }
1418
1419
        $sql = "SELECT count(b.rowid) as nb";
1420
        $sql .= " FROM " . MAIN_DB_PREFIX . "bank as b,";
1421
        $sql .= " " . MAIN_DB_PREFIX . "bank_account as ba";
1422
        $sql .= " WHERE b.fk_account = ba.rowid";
1423
        $sql .= " AND ba.entity IN (" . getEntity('bank_account') . ")";
1424
        $sql .= " AND (ba.rappro = 1 AND ba.courant != 2)"; // Compte rapprochable
1425
        $sql .= " AND clos = 0";
1426
        if ($filteraccountid) {
1427
            $sql .= " AND ba.rowid = " . ((int) $filteraccountid);
1428
        }
1429
1430
        $resql = $this->db->query($sql);
1431
        if ($resql) {
1432
            while ($obj = $this->db->fetch_object($resql)) {
1433
                $this->nb["banklines"] = $obj->nb;
1434
            }
1435
            $this->db->free($resql);
1436
            return 1;
1437
        } else {
1438
            dol_print_error($this->db);
1439
            $this->error = $this->db->error();
1440
            return -1;
1441
        }
1442
    }
1443
1444
1445
    /**
1446
     *      Load indicators for dashboard (this->nbtodo and this->nbtodolate)
1447
     *
1448
     *      @return int     Nb of account we can reconciliate
1449
     */
1450
    public function countAccountToReconcile()
1451
    {
1452
        global $user;
1453
1454
        //Protection against external users
1455
        if ($user->socid) {
1456
            return 0;
1457
        }
1458
1459
        $nb = 0;
1460
1461
        $sql = "SELECT COUNT(ba.rowid) as nb";
1462
        $sql .= " FROM " . MAIN_DB_PREFIX . "bank_account as ba";
1463
        $sql .= " WHERE ba.rappro > 0 and ba.clos = 0";
1464
        $sql .= " AND ba.entity IN (" . getEntity('bank_account') . ")";
1465
        if (!getDolGlobalString('BANK_CAN_RECONCILIATE_CASHACCOUNT')) {
1466
            $sql .= " AND ba.courant != " . Account::TYPE_CASH;
1467
        }
1468
1469
        $resql = $this->db->query($sql);
1470
        if ($resql) {
1471
            $obj = $this->db->fetch_object($resql);
1472
            $nb = $obj->nb;
1473
        } else {
1474
            dol_print_error($this->db);
1475
        }
1476
1477
        return $nb;
1478
    }
1479
1480
    /**
1481
     * getTooltipContentArray
1482
     *
1483
     * @param   array   $params     Params to construct tooltip data
1484
     * @since   v18
1485
     * @return  array
1486
     */
1487
    public function getTooltipContentArray($params)
1488
    {
1489
        global $langs;
1490
        $langs->loadLangs(['banks', 'compta']);
1491
        include_once DOL_DOCUMENT_ROOT . '/core/lib/bank.lib.php';
1492
1493
        $datas = array();
1494
1495
        $nofetch = !empty($params['nofetch']);
1496
        $pictos = img_picto('', $this->picto) . ' <u class="paddingrightnow">' . $langs->trans("BankAccount") . '</u>';
1497
        if (isset($this->status)) {
1498
            $pictos .= ' ' . $this->getLibStatut(5);
1499
        }
1500
        $datas['picto'] = $pictos;
1501
        $datas['label'] = '<br><b>' . $langs->trans('Label') . ':</b> ' . $this->label;
1502
        $datas['accountnumber'] = '<br><b>' . $langs->trans('AccountNumber') . ':</b> ' . $this->number;
1503
        $datas['iban'] = '<br><b>' . $langs->trans('IBAN') . ':</b> ' . getIbanHumanReadable($this);
1504
        $datas['bic'] = '<br><b>' . $langs->trans('BIC') . ':</b> ' . $this->bic;
1505
        $datas['accountcurrency'] = '<br><b>' . $langs->trans("AccountCurrency") . ':</b> ' . $this->currency_code;
1506
1507
        if (isModEnabled('accounting')) {
1508
            include_once DOL_DOCUMENT_ROOT . '/core/lib/accounting.lib.php';
1509
            $langs->load("accountancy");
1510
            $datas['accountaccounting'] = '<br><b>' . $langs->trans('AccountAccounting') . ':</b> ' . length_accountg($this->account_number);
1511
            $datas['accountancyjournal'] = '<br><b>' . $langs->trans('AccountancyJournal') . ':</b> ' . $this->accountancy_journal;
1512
        }
1513
        // show categories for this record only in ajax to not overload lists
1514
        if (isModEnabled('category') && !$nofetch) {
1515
            $form = new Form($this->db);
1516
            $datas['categories'] = '<br>' . $form->showCategories($this->id, Categorie::TYPE_ACCOUNT, 1);
1517
        }
1518
1519
        return $datas;
1520
    }
1521
1522
    /**
1523
     *  Return clicable name (with picto eventually)
1524
     *
1525
     *  @param  int     $withpicto                  Include picto into link
1526
     *  @param  string  $mode                       ''=Link to card, 'transactions'=Link to transactions card
1527
     *  @param  string  $option                     ''=Show ref, 'reflabel'=Show ref+label
1528
     *  @param  int     $save_lastsearch_value      -1=Auto, 0=No save of lastsearch_values when clicking, 1=Save lastsearch_values whenclicking
1529
     *  @param  int     $notooltip                  1=Disable tooltip
1530
     *  @param  string  $morecss                    Add more css on link
1531
     *  @return string                              Chaine avec URL
1532
     */
1533
    public function getNomUrl($withpicto = 0, $mode = '', $option = '', $save_lastsearch_value = -1, $notooltip = 0, $morecss = '')
1534
    {
1535
        global $conf, $langs;
1536
1537
        if (!empty($conf->dol_no_mouse_hover)) {
1538
            $notooltip = 1; // Force disable tooltips
1539
        }
1540
1541
        include_once DOL_DOCUMENT_ROOT . '/core/lib/bank.lib.php';
1542
1543
        $result = '';
1544
        $classfortooltip = 'classfortooltip';
1545
        $dataparams = '';
1546
        $params = [
1547
            'id' => $this->id,
1548
            'objecttype' => $this->element,
1549
            'option' => $option,
1550
            'nofetch' => 1,
1551
        ];
1552
        if (getDolGlobalInt('MAIN_ENABLE_AJAX_TOOLTIP')) {
1553
            $classfortooltip = 'classforajaxtooltip';
1554
            $dataparams = ' data-params="' . dol_escape_htmltag(json_encode($params)) . '"';
1555
            $label = '';
1556
        } else {
1557
            $label = implode($this->getTooltipContentArray($params));
1558
        }
1559
1560
        $url = constant('BASE_URL') . '/compta/bank/card.php?id=' . $this->id;
1561
        if ($mode == 'transactions') {
1562
            $url = constant('BASE_URL') . '/compta/bank/bankentries_list.php?id=' . $this->id;
1563
        } elseif ($mode == 'receipts') {
1564
            $url = constant('BASE_URL') . '/compta/bank/releve.php?account=' . $this->id;
1565
        }
1566
1567
        if ($option != 'nolink') {
1568
            // Add param to save lastsearch_values or not
1569
            $add_save_lastsearch_values = ($save_lastsearch_value == 1 ? 1 : 0);
1570
            if ($save_lastsearch_value == -1 && isset($_SERVER["PHP_SELF"]) && preg_match('/list\.php/', $_SERVER["PHP_SELF"])) {
1571
                $add_save_lastsearch_values = 1;
1572
            }
1573
            if ($add_save_lastsearch_values) {
1574
                $url .= '&save_lastsearch_values=1';
1575
            }
1576
        }
1577
1578
        $linkclose = '';
1579
        if (empty($notooltip)) {
1580
            if (getDolGlobalInt('MAIN_OPTIMIZEFORTEXTBROWSER')) {
1581
                $label = $langs->trans("BankAccount");
1582
                $linkclose .= ' alt="' . dol_escape_htmltag($label, 1) . '"';
1583
            }
1584
            $linkclose .= ($label ? ' title="' . dol_escape_htmltag($label, 1) . '"' : ' title="tocomplete"');
1585
            $linkclose .= $dataparams . ' class="' . $classfortooltip . ($morecss ? ' ' . $morecss : '') . '"';
1586
        } else {
1587
            $linkclose = ($morecss ? ' class="' . $morecss . '"' : '');
1588
        }
1589
1590
        if ($option == 'nolink' || empty($url)) {
1591
            $linkstart = '<span';
1592
        } else {
1593
            $linkstart = '<a href="' . $url . '"';
1594
        }
1595
        $linkstart .= $linkclose . '>';
1596
        if ($option == 'nolink' || empty($url)) {
1597
            $linkend = '</span>';
1598
        } else {
1599
            $linkend = '</a>';
1600
        }
1601
1602
        $result .= $linkstart;
1603
1604
        if ($withpicto) {
1605
            $result .= img_object(($notooltip ? '' : $label), ($this->picto ? $this->picto : 'generic'), ($notooltip ? (($withpicto != 2) ? 'class="paddingright"' : '') : 'class="' . (($withpicto != 2) ? 'paddingright ' : '') . '"'), 0, 0, $notooltip ? 0 : 1);
1606
        }
1607
        if ($withpicto != 2) {
1608
            $result .= $this->ref . ($option == 'reflabel' && $this->label ? ' - ' . $this->label : '');
1609
        }
1610
        $result .= $linkend;
1611
1612
        return $result;
1613
    }
1614
1615
1616
    // Method after here are common to Account and CompanyBankAccount
1617
1618
1619
    /**
1620
     *     Return if an account has valid information for Direct debit payment
1621
     *
1622
     *     @return     int         1 if correct, <=0 if wrong
1623
     */
1624
    public function verif()
1625
    {
1626
        require_once constant('DOL_DOCUMENT_ROOT') . '/core/lib/bank.lib.php';
1627
1628
        $error = 0;
1629
1630
        // Call functions to check BAN
1631
        if (!checkIbanForAccount($this)) {
1632
            $error++;
1633
            $this->error = 'IBANNotValid';
1634
        }
1635
        if (!checkSwiftForAccount($this)) {
1636
            $error++;
1637
            $this->error = 'SwiftNotValid';
1638
        }
1639
1640
        if (! $error) {
1641
            return 1;
1642
        } else {
1643
            return 0;
1644
        }
1645
    }
1646
1647
    /**
1648
     *  Return account country code
1649
     *
1650
     *  @return     string      country code
1651
     */
1652
    public function getCountryCode()
1653
    {
1654
        global $mysoc;
1655
1656
        // We return country code of bank account
1657
        if (!empty($this->country_code)) {
1658
            return $this->country_code;
1659
        }
1660
1661
        // For backward compatibility, we try to guess country from other information
1662
        if (!empty($this->iban)) {
1663
            // If IBAN defined, we can know country of account from it
1664
            $reg = array();
1665
            if (preg_match("/^([a-zA-Z][a-zA-Z])/i", $this->iban, $reg)) {
1666
                return $reg[1];
1667
            }
1668
        }
1669
1670
        // If this class is linked to a third party
1671
        if (!empty($this->socid)) {
1672
            $company = new Societe($this->db);
1673
            $result = $company->fetch($this->socid);
1674
            if (!empty($company->country_code)) {
1675
                return $company->country_code;
1676
            }
1677
        }
1678
1679
        // We return country code of managed company
1680
        if (!empty($mysoc->country_code)) {
1681
            return $mysoc->country_code;
1682
        }
1683
1684
        return '';
1685
    }
1686
1687
    /**
1688
     *  Return full address for banner
1689
     *
1690
     *  @param      string      $htmlkey            HTML id to make banner content unique
1691
     *  @param      Object      $object             Object (thirdparty, thirdparty of contact for contact, null for a member)
1692
     *  @return     string                          Full address string
1693
     */
1694
    public function getBannerAddress($htmlkey, $object)
1695
    {
1696
        global $conf, $langs;
1697
1698
        $out = '';
1699
1700
        $outdone = 0;
1701
        $coords = $this->getFullAddress(1, ', ', getDolGlobalInt('MAIN_SHOW_REGION_IN_STATE_SELECT'));
1702
        if ($coords) {
1703
            if (!empty($conf->use_javascript_ajax)) {
1704
                // hideonsmatphone because copyToClipboard call jquery dialog that does not work with jmobile
1705
                $out .= '<a href="#" class="hideonsmartphone" onclick="return copyToClipboard(\'' . dol_escape_js($coords) . '\',\'' . dol_escape_js($langs->trans("HelpCopyToClipboard")) . '\');">';
1706
                $out .= img_picto($langs->trans("Address"), 'map-marker-alt');
1707
                $out .= '</a> ';
1708
            }
1709
            $address = dol_print_address($coords, 'address_' . $htmlkey . '_' . $this->id, $this->element, $this->id, 1, ', ');
1710
            if ($address) {
1711
                $out .= $address;
1712
                $outdone++;
1713
            }
1714
            $outdone++;
1715
        }
1716
1717
        return $out;
1718
    }
1719
1720
1721
    /**
1722
     * Return if a bank account is defined with detailed information (bank code, desk code, number and key).
1723
     * More information on codes used by countries on page http://en.wikipedia.org/wiki/Bank_code
1724
     *
1725
     * @return      int        0=No bank code need + Account number is enough
1726
     *                         1=Need 2 fields for bank code: Bank, Desk (France, Spain, ...) + Account number and key
1727
     *                         2=Need 1 field for bank code:  Bank only (Sort code for Great Britain, BSB for Australia) + Account number
1728
     */
1729
    public function useDetailedBBAN()
1730
    {
1731
        $country_code = $this->getCountryCode();
1732
1733
        if (in_array($country_code, array('FR', 'ES', 'GA', 'IT', 'NC'))) {
1734
            return 1; // France, Spain, Gabon, ... - Not valid for CH
1735
        }
1736
        if (in_array($country_code, array('AD', 'AU', 'BE', 'CA', 'DE', 'DK', 'GR', 'GB', 'ID', 'IE', 'IR', 'KR', 'NL', 'NZ', 'UK', 'US'))) {
1737
            return 2; // Australia, England...
1738
        }
1739
        return 0;
1740
    }
1741
1742
    /**
1743
     * Return 1 if IBAN / BIC is mandatory (otherwise option)
1744
     *
1745
     * @return      int        1 = mandatory / 0 = Not mandatory
1746
     */
1747
    public function needIBAN()
1748
    {
1749
        global $conf;
1750
1751
        if (getDolGlobalString('MAIN_IBAN_IS_NEVER_MANDATORY')) {
1752
            return 0;
1753
        }
1754
1755
        $country_code = $this->getCountryCode();
1756
1757
        $country_code_in_EEC = array(
1758
                'AT', // Austria
1759
                'BE', // Belgium
1760
                'BG', // Bulgaria
1761
                'CY', // Cyprus
1762
                'CZ', // Czech republic
1763
                'DE', // Germany
1764
                'DK', // Danemark
1765
                'EE', // Estonia
1766
                'ES', // Spain
1767
                'FI', // Finland
1768
                'FR', // France
1769
                'GB', // United Kingdom
1770
                'GR', // Greece
1771
                'HR', // Croatia
1772
                'NL', // Holland
1773
                'HU', // Hungary
1774
                'IE', // Ireland
1775
                'IM', // Isle of Man - Included in UK
1776
                'IT', // Italy
1777
                'LT', // Lithuania
1778
                'LU', // Luxembourg
1779
                'LV', // Latvia
1780
                'MC', // Monaco - Included in France
1781
                'MT', // Malta
1782
                //'NO', // Norway
1783
                'PL', // Poland
1784
                'PT', // Portugal
1785
                'RO', // Romania
1786
                'SE', // Sweden
1787
                'SK', // Slovakia
1788
                'SI', // Slovenia
1789
                'UK', // United Kingdom
1790
                //'CH', // Switzerland - No. Swizerland in not in EEC
1791
        );
1792
1793
        if (in_array($country_code, $country_code_in_EEC)) {
1794
            return 1; // France, Spain, ...
1795
        }
1796
        return 0;
1797
    }
1798
1799
    /**
1800
     *  Load miscellaneous information for tab "Info"
1801
     *
1802
     *  @param  int     $id     Id of object to load
1803
     *  @return void
1804
     */
1805
    public function info($id)
1806
    {
1807
    }
1808
1809
    /**
1810
     * Returns the fields in order that this bank account should show to the user
1811
     * Will return an array with the following values:
1812
     * - BankAccountNumber
1813
     * - BankCode
1814
     * - BankAccountNumberKey
1815
     * - DeskCode
1816
     *
1817
     * Some countries show less or more bank account properties to the user
1818
     *
1819
     * @param  int     $includeibanbic         1=Return also key for IBAN and BIC
1820
     * @return array                           Array of fields to show
1821
     * @see useDetailedBBAN()
1822
     */
1823
    public function getFieldsToShow($includeibanbic = 0)
1824
    {
1825
        //Get the required properties depending on the country
1826
        $detailedBBAN = $this->useDetailedBBAN();
1827
1828
        if ($detailedBBAN == 0) {
1829
            $fieldarray = array(
1830
                    'BankAccountNumber'
1831
            );
1832
        } elseif ($detailedBBAN == 2) {
1833
            $fieldarray = array(
1834
                    'BankCode',
1835
                    'BankAccountNumber'
1836
            );
1837
        } else {
1838
            $fieldarray = self::getAccountNumberOrder();
1839
        }
1840
1841
        //if ($this->needIBAN()) {    // return always IBAN and BIC (this was old behaviour)
1842
        if ($includeibanbic) {
1843
            $fieldarray[] = 'IBAN';
1844
            $fieldarray[] = 'BIC';
1845
        }
1846
        //}
1847
1848
        //Get the order the properties are shown
1849
        return $fieldarray;
1850
    }
1851
1852
    /**
1853
     * Returns the components of the bank account in order.
1854
     * Will return an array with the following values:
1855
     * - BankAccountNumber
1856
     * - BankCode
1857
     * - BankAccountNumberKey
1858
     * - DeskCode
1859
     *
1860
     * @return array
1861
     */
1862
    public static function getAccountNumberOrder()
1863
    {
1864
        global $conf;
1865
1866
        $fieldlists = array(
1867
                'BankCode',
1868
                'DeskCode',
1869
                'BankAccountNumber',
1870
                'BankAccountNumberKey'
1871
        );
1872
1873
        if (getDolGlobalString('BANK_SHOW_ORDER_OPTION')) {
1874
            if (is_numeric(getDolGlobalString('BANK_SHOW_ORDER_OPTION'))) {
1875
                if (getDolGlobalString('BANK_SHOW_ORDER_OPTION') == '1') {
1876
                    $fieldlists = array(
1877
                        'BankCode',
1878
                        'DeskCode',
1879
                        'BankAccountNumberKey',
1880
                        'BankAccountNumber'
1881
                    );
1882
                }
1883
            } else {
1884
                //Replace the old AccountNumber key with the new BankAccountNumber key
1885
                $fieldlists = explode(
1886
                    ' ',
1887
                    preg_replace('/ ?[^Bank]AccountNumber ?/', 'BankAccountNumber', $conf->global->BANK_SHOW_ORDER_OPTION)
1888
                );
1889
            }
1890
        }
1891
1892
        return $fieldlists;
1893
    }
1894
1895
1896
    /**
1897
     *  Initialise an instance with random values.
1898
     *  Used to build previews or test instances.
1899
     *  id must be 0 if object instance is a specimen.
1900
     *
1901
     *  @return int
1902
     */
1903
    public function initAsSpecimen()
1904
    {
1905
        // Example of IBAN FR7630001007941234567890185
1906
        $this->specimen        = 1;
1907
        $this->ref             = 'MBA';
1908
        $this->label           = 'My Big Company Bank account';
1909
        $this->courant         = Account::TYPE_CURRENT;
1910
        $this->clos            = Account::STATUS_OPEN;
0 ignored issues
show
Deprecated Code introduced by
The property Dolibarr\Code\Compta\Classes\Account::$clos has been deprecated: Duplicate field. We already have the field $this->status ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

1910
        /** @scrutinizer ignore-deprecated */ $this->clos            = Account::STATUS_OPEN;

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
1911
        $this->type = Account::TYPE_CURRENT;
1912
        $this->status = Account::STATUS_OPEN;
1913
        $this->code_banque     = '30001';
1914
        $this->code_guichet    = '00794';
1915
        $this->number          = '12345678901';
1916
        $this->cle_rib         = '85';
1917
        $this->bic             = 'AA12';
1918
        $this->iban            = 'FR7630001007941234567890185';
1919
1920
        $this->bank            = 'MyBank';
1921
        $this->address         = 'Rue de Paris';
1922
        $this->proprio         = 'Owner';
1923
        $this->owner_name = 'Owner';
1924
        $this->owner_address   = 'Owner address';
1925
        $this->owner_zip       = 'Owner zip';
1926
        $this->owner_town      = 'Owner town';
1927
        $this->owner_country_id = 'Owner country_id';
1928
        $this->country_id      = 1;
1929
1930
        return 1;
1931
    }
1932
1933
    /**
1934
     * Function used to replace a thirdparty id with another one.
1935
     *
1936
     * @param DoliDB    $dbs            Database handler
1937
     * @param int       $origin_id      Old thirdparty id
1938
     * @param int       $dest_id        New thirdparty id
1939
     * @return bool                     True=SQL success, False=SQL error
1940
     */
1941
    public static function replaceThirdparty($dbs, $origin_id, $dest_id)
1942
    {
1943
        $sql = "UPDATE " . MAIN_DB_PREFIX . "bank_url SET url_id = " . ((int) $dest_id) . " WHERE url_id = " . ((int) $origin_id) . " AND type='company'";
1944
1945
        if ($dbs->query($sql)) {
1946
            return true;
1947
        } else {
1948
            //if ($ignoreerrors) return true; // TODO Not enough. If there is A-B on kept thirdparty and B-C on old one, we must get A-B-C after merge. Not A-B.
1949
            //$this->errors = $dbs->lasterror();
1950
            return false;
1951
        }
1952
    }
1953
1954
    /**
1955
     *  Return clicable link of object (with eventually picto)
1956
     *
1957
     *  @param      string      $option                 Where point the link (0=> main card, 1,2 => shipment, 'nolink'=>No link)
1958
     *  @param      array       $arraydata              Array of data
1959
     *  @return     string                              HTML Code for Kanban thumb.
1960
     */
1961
    public function getKanbanView($option = '', $arraydata = null)
1962
    {
1963
        global $langs;
1964
1965
        $selected = (empty($arraydata['selected']) ? 0 : $arraydata['selected']);
1966
1967
        $return = '<div class="box-flex-item box-flex-grow-zero">';
1968
        $return .= '<div class="info-box info-box-sm">';
1969
        $return .= '<span class="info-box-icon bg-infobox-action">';
1970
        $return .= img_picto('', $this->picto);
1971
        $return .= '</span>';
1972
        $return .= '<div class="info-box-content">';
1973
        $return .= '<span class="info-box-ref inline-block tdoverflowmax150 valignmiddle">' . (method_exists($this, 'getNomUrl') ? $this->getNomUrl() : $this->ref) . '</span>';
1974
        if ($selected >= 0) {
1975
            $return .= '<input id="cb' . $this->id . '" class="flat checkforselect fright" type="checkbox" name="toselect[]" value="' . $this->id . '"' . ($selected ? ' checked="checked"' : '') . '>';
1976
        }
1977
        if (property_exists($this, 'type_lib')) {
1978
            $return .= '<br><span class="info-box-label opacitymedium" title="' . $this->type_lib[$this->type] . '">' . substr($this->type_lib[$this->type], 0, 24) . '...</span>';
1979
        }
1980
        if (method_exists($this, 'solde')) {
1981
            $return .= '<br><a href="' . constant('BASE_URL') . '/compta/bank/bankentries_list.php?id=' . $this->id . '">';
1982
            $return .= '<span class="opacitymedium">' . $langs->trans("Balance") . '</span> : <span class="amount">' . price(price2num($this->solde(1), 'MT'), 0, $langs, 1, -1, -1, $this->currency_code) . '</span>';
1983
        }
1984
        if (method_exists($this, 'getLibStatut')) {
1985
            $return .= '<br><div class="info-box-status">' . $this->getLibStatut(3) . '</div>';
1986
        }
1987
        $return .= '</div>';
1988
        $return .= '</div>';
1989
        $return .= '</div>';
1990
        return $return;
1991
    }
1992
}
1993