societe.class.php 129 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730273127322733273427352736273727382739274027412742274327442745274627472748274927502751275227532754275527562757275827592760276127622763276427652766276727682769277027712772277327742775277627772778277927802781278227832784278527862787278827892790279127922793279427952796279727982799280028012802280328042805280628072808280928102811281228132814281528162817281828192820282128222823282428252826282728282829283028312832283328342835283628372838283928402841284228432844284528462847284828492850285128522853285428552856285728582859286028612862286328642865286628672868286928702871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940294129422943294429452946294729482949295029512952295329542955295629572958295929602961296229632964296529662967296829692970297129722973297429752976297729782979298029812982298329842985298629872988298929902991299229932994299529962997299829993000300130023003300430053006300730083009301030113012301330143015301630173018301930203021302230233024302530263027302830293030303130323033303430353036303730383039304030413042304330443045304630473048304930503051305230533054305530563057305830593060306130623063306430653066306730683069307030713072307330743075307630773078307930803081308230833084308530863087308830893090309130923093309430953096309730983099310031013102310331043105310631073108310931103111311231133114311531163117311831193120312131223123312431253126312731283129313031313132313331343135313631373138313931403141314231433144314531463147314831493150315131523153315431553156315731583159316031613162316331643165316631673168316931703171317231733174317531763177317831793180318131823183318431853186318731883189319031913192319331943195319631973198319932003201320232033204320532063207320832093210321132123213321432153216321732183219322032213222322332243225322632273228322932303231323232333234323532363237323832393240324132423243324432453246324732483249325032513252325332543255325632573258325932603261326232633264326532663267326832693270327132723273327432753276327732783279328032813282328332843285328632873288328932903291329232933294329532963297329832993300330133023303330433053306330733083309331033113312331333143315331633173318331933203321332233233324332533263327332833293330333133323333333433353336333733383339334033413342334333443345334633473348334933503351335233533354335533563357335833593360336133623363336433653366336733683369337033713372337333743375337633773378337933803381338233833384338533863387338833893390339133923393339433953396339733983399340034013402340334043405340634073408340934103411341234133414341534163417341834193420342134223423342434253426342734283429343034313432343334343435343634373438343934403441344234433444344534463447344834493450345134523453345434553456345734583459346034613462346334643465346634673468346934703471347234733474347534763477347834793480348134823483348434853486348734883489349034913492349334943495349634973498349935003501350235033504350535063507350835093510351135123513351435153516351735183519352035213522352335243525352635273528352935303531353235333534353535363537353835393540354135423543354435453546354735483549355035513552355335543555355635573558355935603561356235633564356535663567356835693570357135723573357435753576357735783579358035813582358335843585358635873588358935903591359235933594359535963597359835993600360136023603360436053606360736083609361036113612361336143615361636173618361936203621362236233624362536263627362836293630363136323633363436353636363736383639364036413642364336443645364636473648364936503651365236533654365536563657365836593660366136623663366436653666366736683669367036713672367336743675367636773678367936803681368236833684368536863687368836893690369136923693369436953696369736983699370037013702370337043705370637073708
  1. <?php
  2. /* Copyright (C) 2002-2006 Rodolphe Quiedeville <rodolphe@quiedeville.org>
  3. * Copyright (C) 2004-2015 Laurent Destailleur <eldy@users.sourceforge.net>
  4. * Copyright (C) 2004 Eric Seigne <eric.seigne@ryxeo.com>
  5. * Copyright (C) 2003 Brian Fraval <brian@fraval.org>
  6. * Copyright (C) 2006 Andre Cianfarani <acianfa@free.fr>
  7. * Copyright (C) 2005-2016 Regis Houssin <regis.houssin@capnetworks.com>
  8. * Copyright (C) 2008 Patrick Raguin <patrick.raguin@auguria.net>
  9. * Copyright (C) 2010-2014 Juanjo Menent <jmenent@2byte.es>
  10. * Copyright (C) 2013 Florian Henry <florian.henry@open-concept.pro>
  11. * Copyright (C) 2013 Alexandre Spangaro <aspangaro.dolibarr@gmail.com>
  12. * Copyright (C) 2013 Peter Fontaine <contact@peterfontaine.fr>
  13. * Copyright (C) 2014-2015 Marcos García <marcosgdf@gmail.com>
  14. * Copyright (C) 2015 Raphaël Doursenaud <rdoursenaud@gpcsolutions.fr>
  15. *
  16. * This program is free software; you can redistribute it and/or modify
  17. * it under the terms of the GNU General Public License as published by
  18. * the Free Software Foundation; either version 3 of the License, or
  19. * (at your option) any later version.
  20. *
  21. * This program is distributed in the hope that it will be useful,
  22. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  23. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  24. * GNU General Public License for more details.
  25. *
  26. * You should have received a copy of the GNU General Public License
  27. * along with this program. If not, see <http://www.gnu.org/licenses/>.
  28. */
  29. /**
  30. * \file htdocs/societe/class/societe.class.php
  31. * \ingroup societe
  32. * \brief File for third party class
  33. */
  34. require_once DOL_DOCUMENT_ROOT.'/core/class/commonobject.class.php';
  35. require_once DOL_DOCUMENT_ROOT.'/multicurrency/class/multicurrency.class.php';
  36. /**
  37. * Class to manage third parties objects (customers, suppliers, prospects...)
  38. */
  39. class Societe extends CommonObject
  40. {
  41. public $element='societe';
  42. public $table_element = 'societe';
  43. public $fk_element='fk_soc';
  44. protected $childtables=array("supplier_proposal","propal","commande","facture","contrat","facture_fourn","commande_fournisseur","projet","expedition"); // To test if we can delete object
  45. /**
  46. * 0=No test on entity, 1=Test with field entity, 2=Test with link by societe
  47. * @var int
  48. */
  49. protected $ismultientitymanaged = 1;
  50. public $entity;
  51. /**
  52. * Thirdparty name
  53. * @var string
  54. * @deprecated Use $name instead
  55. * @see name
  56. */
  57. public $nom;
  58. /**
  59. * Alias names (commercial, trademark or alias names)
  60. * @var string
  61. */
  62. public $name_alias;
  63. public $particulier;
  64. public $address;
  65. public $zip;
  66. public $town;
  67. /**
  68. * Thirdparty status : 0=activity ceased, 1= in activity
  69. * @var int
  70. */
  71. var $status;
  72. /**
  73. * Id of department
  74. * @var int
  75. */
  76. var $state_id;
  77. var $state_code;
  78. var $state;
  79. /**
  80. * State code
  81. * @var string
  82. * @deprecated Use state_code instead
  83. * @see state_code
  84. */
  85. var $departement_code;
  86. /**
  87. * @var string
  88. * @deprecated Use state instead
  89. * @see state
  90. */
  91. var $departement;
  92. /**
  93. * @var string
  94. * @deprecated Use country instead
  95. * @see country
  96. */
  97. var $pays;
  98. /**
  99. * Phone number
  100. * @var string
  101. */
  102. var $phone;
  103. /**
  104. * Fax number
  105. * @var string
  106. */
  107. var $fax;
  108. /**
  109. * Email
  110. * @var string
  111. */
  112. var $email;
  113. /**
  114. * Skype username
  115. * @var string
  116. */
  117. var $skype;
  118. /**
  119. * Webpage
  120. * @var string
  121. */
  122. var $url;
  123. //! barcode
  124. /**
  125. * Barcode value
  126. * @var string
  127. */
  128. var $barcode;
  129. // 6 professional id (usage depends on country)
  130. /**
  131. * Professional ID 1 (Ex: Siren in France)
  132. * @var string
  133. */
  134. var $idprof1;
  135. /**
  136. * Professional ID 2 (Ex: Siret in France)
  137. * @var string
  138. */
  139. var $idprof2;
  140. /**
  141. * Professional ID 3 (Ex: Ape in France)
  142. * @var string
  143. */
  144. var $idprof3;
  145. /**
  146. * Professional ID 4 (Ex: RCS in France)
  147. * @var string
  148. */
  149. var $idprof4;
  150. /**
  151. * Professional ID 5
  152. * @var string
  153. */
  154. var $idprof5;
  155. /**
  156. * Professional ID 6
  157. * @var string
  158. */
  159. var $idprof6;
  160. var $prefix_comm;
  161. var $tva_assuj;
  162. /**
  163. * Intracommunitary VAT ID
  164. * @var string
  165. */
  166. var $tva_intra;
  167. // Local taxes
  168. var $localtax1_assuj;
  169. var $localtax1_value;
  170. var $localtax2_assuj;
  171. var $localtax2_value;
  172. var $managers;
  173. var $capital;
  174. var $typent_id;
  175. var $typent_code;
  176. var $effectif;
  177. var $effectif_id;
  178. var $forme_juridique_code;
  179. var $forme_juridique;
  180. var $remise_percent;
  181. var $mode_reglement_supplier_id;
  182. var $cond_reglement_supplier_id;
  183. var $fk_prospectlevel;
  184. var $name_bis;
  185. //Log data
  186. /**
  187. * Date of last update
  188. * @var string
  189. */
  190. var $date_modification;
  191. /**
  192. * User that made last update
  193. * @var string
  194. */
  195. var $user_modification;
  196. /**
  197. * Date of creation
  198. * @var string
  199. */
  200. var $date_creation;
  201. /**
  202. * User that created the thirdparty
  203. * @var User
  204. */
  205. var $user_creation;
  206. var $specimen;
  207. /**
  208. * 0=no customer, 1=customer, 2=prospect, 3=customer and prospect
  209. * @var int
  210. */
  211. var $client;
  212. /**
  213. * 0=no prospect, 1=prospect
  214. * @var int
  215. */
  216. var $prospect;
  217. /**
  218. * 0=no supplier, 1=supplier
  219. * @var int
  220. */
  221. var $fournisseur;
  222. /**
  223. * Client code. E.g: CU2014-003
  224. * @var string
  225. */
  226. var $code_client;
  227. /**
  228. * Supplier code. E.g: SU2014-003
  229. * @var string
  230. */
  231. var $code_fournisseur;
  232. /**
  233. * Accounting code for client
  234. * @var string
  235. */
  236. var $code_compta;
  237. /**
  238. * Accounting code for suppliers
  239. * @var string
  240. */
  241. var $code_compta_fournisseur;
  242. /**
  243. * @var string
  244. * @deprecated Note is split in public and private notes
  245. * @see note_public, note_private
  246. */
  247. var $note;
  248. /**
  249. * Private note
  250. * @var string
  251. */
  252. var $note_private;
  253. /**
  254. * Public note
  255. * @var string
  256. */
  257. var $note_public;
  258. //! code statut prospect
  259. var $stcomm_id;
  260. var $statut_commercial;
  261. /**
  262. * Assigned price level
  263. * @var int
  264. */
  265. var $price_level;
  266. var $outstanding_limit;
  267. /**
  268. * Id of sales representative to link (used for thirdparty creation). Not filled by a fetch, because we can have several sales representatives.
  269. * @var int
  270. */
  271. var $commercial_id;
  272. /**
  273. * Id of parent thirdparty (if one)
  274. * @var int
  275. */
  276. var $parent;
  277. /**
  278. * Default language code of thirdparty (en_US, ...)
  279. * @var string
  280. */
  281. var $default_lang;
  282. var $ref;
  283. var $ref_int;
  284. /**
  285. * External user reference.
  286. * This is to allow external systems to store their id and make self-developed synchronizing functions easier to
  287. * build.
  288. * @var string
  289. */
  290. var $ref_ext;
  291. /**
  292. * Import key.
  293. * Set when the thirdparty has been created through an import process. This is to relate those created thirdparties
  294. * to an import process
  295. * @var string
  296. */
  297. var $import_key;
  298. /**
  299. * Supplier WebServices URL
  300. * @var string
  301. */
  302. var $webservices_url;
  303. /**
  304. * Supplier WebServices Key
  305. * @var string
  306. */
  307. var $webservices_key;
  308. var $logo;
  309. var $logo_small;
  310. var $logo_mini;
  311. var $array_options;
  312. // Incoterms
  313. var $fk_incoterms;
  314. var $location_incoterms;
  315. var $libelle_incoterms; //Used into tooltip
  316. // Multicurrency
  317. var $fk_multicurrency;
  318. var $multicurrency_code;
  319. /**
  320. * To contains a clone of this when we need to save old properties of object
  321. * @var Societe
  322. */
  323. var $oldcopy;
  324. /**
  325. * Constructor
  326. *
  327. * @param DoliDB $db Database handler
  328. */
  329. public function __construct($db)
  330. {
  331. $this->db = $db;
  332. $this->client = 0;
  333. $this->prospect = 0;
  334. $this->fournisseur = 0;
  335. $this->typent_id = 0;
  336. $this->effectif_id = 0;
  337. $this->forme_juridique_code = 0;
  338. $this->tva_assuj = 1;
  339. $this->status = 1;
  340. }
  341. /**
  342. * Create third party in database
  343. *
  344. * @param User $user Object of user that ask creation
  345. * @return int >= 0 if OK, < 0 if KO
  346. */
  347. function create($user)
  348. {
  349. global $langs,$conf;
  350. $error=0;
  351. // Clean parameters
  352. if (empty($this->status)) $this->status=0;
  353. $this->name=$this->name?trim($this->name):trim($this->nom);
  354. if (! empty($conf->global->MAIN_FIRST_TO_UPPER)) $this->name=ucwords($this->name);
  355. $this->nom=$this->name; // For backward compatibility
  356. if (empty($this->client)) $this->client=0;
  357. if (empty($this->fournisseur)) $this->fournisseur=0;
  358. $this->import_key = trim($this->import_key);
  359. if (!empty($this->multicurrency_code)) $this->fk_multicurrency = MultiCurrency::getIdFromCode($this->db, $this->multicurrency_code);
  360. if (empty($this->fk_multicurrency))
  361. {
  362. $this->multicurrency_code = '';
  363. $this->fk_multicurrency = 0;
  364. }
  365. dol_syslog(get_class($this)."::create ".$this->name);
  366. // Check parameters
  367. if (! empty($conf->global->SOCIETE_MAIL_REQUIRED) && ! isValidEMail($this->email))
  368. {
  369. $langs->load("errors");
  370. $this->error = $langs->trans("ErrorBadEMail",$this->email);
  371. return -1;
  372. }
  373. $now=dol_now();
  374. $this->db->begin();
  375. // For automatic creation during create action (not used by Dolibarr GUI, can be used by scripts)
  376. if ($this->code_client == -1) $this->get_codeclient($this,0);
  377. if ($this->code_fournisseur == -1) $this->get_codefournisseur($this,1);
  378. // Check more parameters
  379. // If error, this->errors[] is filled
  380. $result = $this->verify();
  381. if ($result >= 0)
  382. {
  383. $sql = "INSERT INTO ".MAIN_DB_PREFIX."societe (nom, name_alias, entity, datec, fk_user_creat, canvas, status, ref_int, ref_ext, fk_stcomm, fk_incoterms, location_incoterms ,import_key, fk_multicurrency, multicurrency_code)";
  384. $sql.= " VALUES ('".$this->db->escape($this->name)."', '".$this->db->escape($this->name_alias)."', ".$conf->entity.", '".$this->db->idate($now)."'";
  385. $sql.= ", ".(! empty($user->id) ? "'".$user->id."'":"null");
  386. $sql.= ", ".(! empty($this->canvas) ? "'".$this->db->escape($this->canvas)."'":"null");
  387. $sql.= ", ".$this->status;
  388. $sql.= ", ".(! empty($this->ref_int) ? "'".$this->db->escape($this->ref_int)."'":"null");
  389. $sql.= ", ".(! empty($this->ref_ext) ? "'".$this->db->escape($this->ref_ext)."'":"null");
  390. $sql.= ", 0";
  391. $sql.= ", ".(int) $this->fk_incoterms;
  392. $sql.= ", '".$this->db->escape($this->location_incoterms)."'";
  393. $sql.= ", ".(! empty($this->import_key) ? "'".$this->db->escape($this->import_key)."'":"null");
  394. $sql.= ", ".(int) $this->fk_multicurrency;
  395. $sql.= ", '".$this->db->escape($this->multicurrency_code)."')";
  396. dol_syslog(get_class($this)."::create", LOG_DEBUG);
  397. $result=$this->db->query($sql);
  398. if ($result)
  399. {
  400. $this->id = $this->db->last_insert_id(MAIN_DB_PREFIX."societe");
  401. $ret = $this->update($this->id,$user,0,1,1,'add');
  402. // Ajout du commercial affecte
  403. if ($this->commercial_id != '' && $this->commercial_id != -1)
  404. {
  405. $this->add_commercial($user, $this->commercial_id);
  406. }
  407. // si un commercial cree un client il lui est affecte automatiquement
  408. else if (empty($user->rights->societe->client->voir))
  409. {
  410. $this->add_commercial($user, $user->id);
  411. }
  412. if ($ret >= 0)
  413. {
  414. // Call trigger
  415. $result=$this->call_trigger('COMPANY_CREATE',$user);
  416. if ($result < 0) $error++;
  417. // End call triggers
  418. }
  419. else $error++;
  420. if (! $error)
  421. {
  422. dol_syslog(get_class($this)."::Create success id=".$this->id);
  423. $this->db->commit();
  424. return $this->id;
  425. }
  426. else
  427. {
  428. dol_syslog(get_class($this)."::Create echec update ".$this->error." ".join(',',$this->errors), LOG_ERR);
  429. $this->db->rollback();
  430. return -4;
  431. }
  432. }
  433. else
  434. {
  435. if ($this->db->lasterrno() == 'DB_ERROR_RECORD_ALREADY_EXISTS')
  436. {
  437. $this->error=$langs->trans("ErrorCompanyNameAlreadyExists",$this->name); // duplicate on a field (code or profid or ...)
  438. $result=-1;
  439. }
  440. else
  441. {
  442. $this->error=$this->db->lasterror();
  443. $result=-2;
  444. }
  445. $this->db->rollback();
  446. return $result;
  447. }
  448. }
  449. else
  450. {
  451. $this->db->rollback();
  452. dol_syslog(get_class($this)."::Create fails verify ".join(',',$this->errors), LOG_WARNING);
  453. return -3;
  454. }
  455. }
  456. /**
  457. * Create a contact/address from thirdparty
  458. *
  459. * @param User $user Object user
  460. * @return int <0 if KO, >0 if OK
  461. */
  462. function create_individual(User $user)
  463. {
  464. require_once DOL_DOCUMENT_ROOT.'/contact/class/contact.class.php';
  465. $contact=new Contact($this->db);
  466. $contact->name = $this->name_bis;
  467. $contact->firstname = $this->firstname;
  468. $contact->civility_id = $this->civility_id;
  469. $contact->socid = $this->id; // fk_soc
  470. $contact->statut = 1;
  471. $contact->priv = 0;
  472. $contact->country_id = $this->country_id;
  473. $contact->state_id = $this->state_id;
  474. $contact->address = $this->address;
  475. $contact->email = $this->email;
  476. $contact->zip = $this->zip;
  477. $contact->town = $this->town;
  478. $contact->phone_pro = $this->phone;
  479. $result = $contact->create($user);
  480. if ($result < 0)
  481. {
  482. $this->error = $contact->error;
  483. $this->errors = $contact->errors;
  484. dol_syslog(get_class($this)."::create_individual ERROR:" . $this->error, LOG_ERR);
  485. }
  486. return $result;
  487. }
  488. /**
  489. * Check properties of third party are ok (like name, third party codes, ...)
  490. * Used before an add or update.
  491. *
  492. * @return int 0 if OK, <0 if KO
  493. */
  494. function verify()
  495. {
  496. $this->errors=array();
  497. $result = 0;
  498. $this->name = trim($this->name);
  499. $this->nom=$this->name; // For backward compatibility
  500. if (! $this->name)
  501. {
  502. $this->errors[] = 'ErrorBadThirdPartyName';
  503. $result = -2;
  504. }
  505. if ($this->client)
  506. {
  507. $rescode = $this->check_codeclient();
  508. if ($rescode <> 0)
  509. {
  510. if ($rescode == -1)
  511. {
  512. $this->errors[] = 'ErrorBadCustomerCodeSyntax';
  513. }
  514. if ($rescode == -2)
  515. {
  516. $this->errors[] = 'ErrorCustomerCodeRequired';
  517. }
  518. if ($rescode == -3)
  519. {
  520. $this->errors[] = 'ErrorCustomerCodeAlreadyUsed';
  521. }
  522. if ($rescode == -4)
  523. {
  524. $this->errors[] = 'ErrorPrefixRequired';
  525. }
  526. $result = -3;
  527. }
  528. }
  529. if ($this->fournisseur)
  530. {
  531. $rescode = $this->check_codefournisseur();
  532. if ($rescode <> 0)
  533. {
  534. if ($rescode == -1)
  535. {
  536. $this->errors[] = 'ErrorBadSupplierCodeSyntax';
  537. }
  538. if ($rescode == -2)
  539. {
  540. $this->errors[] = 'ErrorSupplierCodeRequired';
  541. }
  542. if ($rescode == -3)
  543. {
  544. $this->errors[] = 'ErrorSupplierCodeAlreadyUsed';
  545. }
  546. if ($rescode == -5)
  547. {
  548. $this->errors[] = 'ErrorprefixRequired';
  549. }
  550. $result = -3;
  551. }
  552. }
  553. return $result;
  554. }
  555. /**
  556. * Update parameters of third party
  557. *
  558. * @param int $id id societe
  559. * @param User $user Utilisateur qui demande la mise a jour
  560. * @param int $call_trigger 0=non, 1=oui
  561. * @param int $allowmodcodeclient Inclut modif code client et code compta
  562. * @param int $allowmodcodefournisseur Inclut modif code fournisseur et code compta fournisseur
  563. * @param string $action 'add' or 'update'
  564. * @param int $nosyncmember Do not synchronize info of linked member
  565. * @return int <0 if KO, >=0 if OK
  566. */
  567. function update($id, $user='', $call_trigger=1, $allowmodcodeclient=0, $allowmodcodefournisseur=0, $action='update', $nosyncmember=1)
  568. {
  569. global $langs,$conf,$hookmanager;
  570. require_once DOL_DOCUMENT_ROOT.'/core/lib/functions2.lib.php';
  571. $error=0;
  572. dol_syslog(get_class($this)."::Update id=".$id." call_trigger=".$call_trigger." allowmodcodeclient=".$allowmodcodeclient." allowmodcodefournisseur=".$allowmodcodefournisseur);
  573. $now=dol_now();
  574. // Clean parameters
  575. $this->id = $id;
  576. $this->name = $this->name?trim($this->name):trim($this->nom);
  577. $this->nom = $this->name; // For backward compatibility
  578. $this->name_alias = trim($this->name_alias);
  579. $this->ref_ext = trim($this->ref_ext);
  580. $this->address = $this->address?trim($this->address):trim($this->address);
  581. $this->zip = $this->zip?trim($this->zip):trim($this->zip);
  582. $this->town = $this->town?trim($this->town):trim($this->town);
  583. $this->state_id = trim($this->state_id);
  584. $this->country_id = ($this->country_id > 0)?$this->country_id:0;
  585. $this->phone = trim($this->phone);
  586. $this->phone = preg_replace("/\s/","",$this->phone);
  587. $this->phone = preg_replace("/\./","",$this->phone);
  588. $this->fax = trim($this->fax);
  589. $this->fax = preg_replace("/\s/","",$this->fax);
  590. $this->fax = preg_replace("/\./","",$this->fax);
  591. $this->email = trim($this->email);
  592. $this->skype = trim($this->skype);
  593. $this->url = $this->url?clean_url($this->url,0):'';
  594. $this->idprof1 = trim($this->idprof1);
  595. $this->idprof2 = trim($this->idprof2);
  596. $this->idprof3 = trim($this->idprof3);
  597. $this->idprof4 = trim($this->idprof4);
  598. $this->idprof5 = (! empty($this->idprof5)?trim($this->idprof5):'');
  599. $this->idprof6 = (! empty($this->idprof6)?trim($this->idprof6):'');
  600. $this->prefix_comm = trim($this->prefix_comm);
  601. $this->outstanding_limit = price2num($this->outstanding_limit);
  602. $this->tva_assuj = trim($this->tva_assuj);
  603. $this->tva_intra = dol_sanitizeFileName($this->tva_intra,'');
  604. if (empty($this->status)) $this->status = 0;
  605. if (!empty($this->multicurrency_code)) $this->fk_multicurrency = MultiCurrency::getIdFromCode($this->db, $this->multicurrency_code);
  606. if (empty($this->fk_multicurrency))
  607. {
  608. $this->multicurrency_code = '';
  609. $this->fk_multicurrency = 0;
  610. }
  611. // Local taxes
  612. $this->localtax1_assuj=trim($this->localtax1_assuj);
  613. $this->localtax2_assuj=trim($this->localtax2_assuj);
  614. $this->localtax1_value=trim($this->localtax1_value);
  615. $this->localtax2_value=trim($this->localtax2_value);
  616. if ($this->capital != '') $this->capital=price2num(trim($this->capital));
  617. if (! is_numeric($this->capital)) $this->capital = ''; // '' = undef
  618. $this->effectif_id=trim($this->effectif_id);
  619. $this->forme_juridique_code=trim($this->forme_juridique_code);
  620. //Gencod
  621. $this->barcode=trim($this->barcode);
  622. // For automatic creation
  623. if ($this->code_client == -1) $this->get_codeclient($this,0);
  624. if ($this->code_fournisseur == -1) $this->get_codefournisseur($this,1);
  625. $this->code_compta=trim($this->code_compta);
  626. $this->code_compta_fournisseur=trim($this->code_compta_fournisseur);
  627. // Check parameters
  628. if (! empty($conf->global->SOCIETE_MAIL_REQUIRED) && ! isValidEMail($this->email))
  629. {
  630. $langs->load("errors");
  631. $this->error = $langs->trans("ErrorBadEMail",$this->email);
  632. return -1;
  633. }
  634. if (! is_numeric($this->client) && ! is_numeric($this->fournisseur))
  635. {
  636. $langs->load("errors");
  637. $this->error = $langs->trans("BadValueForParameterClientOrSupplier");
  638. return -1;
  639. }
  640. $customer=false;
  641. if (! empty($allowmodcodeclient) && ! empty($this->client))
  642. {
  643. // Attention get_codecompta peut modifier le code suivant le module utilise
  644. if (empty($this->code_compta))
  645. {
  646. $ret=$this->get_codecompta('customer');
  647. if ($ret < 0) return -1;
  648. }
  649. $customer=true;
  650. }
  651. $supplier=false;
  652. if (! empty($allowmodcodefournisseur) && ! empty($this->fournisseur))
  653. {
  654. // Attention get_codecompta peut modifier le code suivant le module utilise
  655. if (empty($this->code_compta_fournisseur))
  656. {
  657. $ret=$this->get_codecompta('supplier');
  658. if ($ret < 0) return -1;
  659. }
  660. $supplier=true;
  661. }
  662. //Web services
  663. $this->webservices_url = $this->webservices_url?clean_url($this->webservices_url,0):'';
  664. $this->webservices_key = trim($this->webservices_key);
  665. //Incoterms
  666. $this->fk_incoterms = (int) $this->fk_incoterms;
  667. $this->location_incoterms = trim($this->location_incoterms);
  668. $this->db->begin();
  669. // Check name is required and codes are ok or unique.
  670. // If error, this->errors[] is filled
  671. $result = 0;
  672. if ($action != 'add') $result = $this->verify(); // We don't check when update called during a create because verify was already done
  673. if ($result >= 0)
  674. {
  675. dol_syslog(get_class($this)."::update verify ok or not done");
  676. $sql = "UPDATE ".MAIN_DB_PREFIX."societe SET ";
  677. $sql .= "nom = '" . $this->db->escape($this->name) ."'"; // Required
  678. $sql .= ",name_alias = '" . $this->db->escape($this->name_alias) ."'";
  679. $sql .= ",ref_ext = " .(! empty($this->ref_ext)?"'".$this->db->escape($this->ref_ext) ."'":"null");
  680. $sql .= ",address = '" . $this->db->escape($this->address) ."'";
  681. $sql .= ",zip = ".(! empty($this->zip)?"'".$this->db->escape($this->zip)."'":"null");
  682. $sql .= ",town = ".(! empty($this->town)?"'".$this->db->escape($this->town)."'":"null");
  683. $sql .= ",fk_departement = '" . (! empty($this->state_id)?$this->state_id:'0') ."'";
  684. $sql .= ",fk_pays = '" . (! empty($this->country_id)?$this->country_id:'0') ."'";
  685. $sql .= ",phone = ".(! empty($this->phone)?"'".$this->db->escape($this->phone)."'":"null");
  686. $sql .= ",fax = ".(! empty($this->fax)?"'".$this->db->escape($this->fax)."'":"null");
  687. $sql .= ",email = ".(! empty($this->email)?"'".$this->db->escape($this->email)."'":"null");
  688. $sql .= ",skype = ".(! empty($this->skype)?"'".$this->db->escape($this->skype)."'":"null");
  689. $sql .= ",url = ".(! empty($this->url)?"'".$this->db->escape($this->url)."'":"null");
  690. $sql .= ",siren = '". $this->db->escape($this->idprof1) ."'";
  691. $sql .= ",siret = '". $this->db->escape($this->idprof2) ."'";
  692. $sql .= ",ape = '". $this->db->escape($this->idprof3) ."'";
  693. $sql .= ",idprof4 = '". $this->db->escape($this->idprof4) ."'";
  694. $sql .= ",idprof5 = '". $this->db->escape($this->idprof5) ."'";
  695. $sql .= ",idprof6 = '". $this->db->escape($this->idprof6) ."'";
  696. $sql .= ",tva_assuj = ".($this->tva_assuj!=''?"'".$this->tva_assuj."'":"null");
  697. $sql .= ",tva_intra = '" . $this->db->escape($this->tva_intra) ."'";
  698. $sql .= ",status = " .$this->status;
  699. // Local taxes
  700. $sql .= ",localtax1_assuj = ".($this->localtax1_assuj!=''?"'".$this->localtax1_assuj."'":"null");
  701. $sql .= ",localtax2_assuj = ".($this->localtax2_assuj!=''?"'".$this->localtax2_assuj."'":"null");
  702. if($this->localtax1_assuj==1)
  703. {
  704. if($this->localtax1_value!='')
  705. {
  706. $sql .=",localtax1_value =".$this->localtax1_value;
  707. }
  708. else $sql .=",localtax1_value =0.000";
  709. }
  710. else $sql .=",localtax1_value =0.000";
  711. if($this->localtax2_assuj==1)
  712. {
  713. if($this->localtax2_value!='')
  714. {
  715. $sql .=",localtax2_value =".$this->localtax2_value;
  716. }
  717. else $sql .=",localtax2_value =0.000";
  718. }
  719. else $sql .=",localtax2_value =0.000";
  720. $sql .= ",capital = ".($this->capital == '' ? "null" : $this->capital);
  721. $sql .= ",prefix_comm = ".(! empty($this->prefix_comm)?"'".$this->db->escape($this->prefix_comm)."'":"null");
  722. $sql .= ",fk_effectif = ".(! empty($this->effectif_id)?"'".$this->db->escape($this->effectif_id)."'":"null");
  723. if (isset($this->stcomm_id))
  724. {
  725. $sql .= ",fk_stcomm=".($this->stcomm_id > 0 ? $this->stcomm_id : "0");
  726. }
  727. $sql .= ",fk_typent = ".(! empty($this->typent_id)?"'".$this->db->escape($this->typent_id)."'":"0");
  728. $sql .= ",fk_forme_juridique = ".(! empty($this->forme_juridique_code)?"'".$this->db->escape($this->forme_juridique_code)."'":"null");
  729. $sql .= ",mode_reglement = ".(! empty($this->mode_reglement_id)?"'".$this->db->escape($this->mode_reglement_id)."'":"null");
  730. $sql .= ",cond_reglement = ".(! empty($this->cond_reglement_id)?"'".$this->db->escape($this->cond_reglement_id)."'":"null");
  731. $sql .= ",mode_reglement_supplier = ".(! empty($this->mode_reglement_supplier_id)?"'".$this->db->escape($this->mode_reglement_supplier_id)."'":"null");
  732. $sql .= ",cond_reglement_supplier = ".(! empty($this->cond_reglement_supplier_id)?"'".$this->db->escape($this->cond_reglement_supplier_id)."'":"null");
  733. $sql .= ",fk_shipping_method = ".(! empty($this->shipping_method_id)?"'".$this->db->escape($this->shipping_method_id)."'":"null");
  734. $sql .= ",client = " . (! empty($this->client)?$this->client:0);
  735. $sql .= ",fournisseur = " . (! empty($this->fournisseur)?$this->fournisseur:0);
  736. $sql .= ",barcode = ".(! empty($this->barcode)?"'".$this->db->escape($this->barcode)."'":"null");
  737. $sql .= ",default_lang = ".(! empty($this->default_lang)?"'".$this->db->escape($this->default_lang)."'":"null");
  738. $sql .= ",logo = ".(! empty($this->logo)?"'".$this->db->escape($this->logo)."'":"null");
  739. $sql .= ",outstanding_limit= ".($this->outstanding_limit!=''?$this->outstanding_limit:'null');
  740. $sql .= ",fk_prospectlevel='".$this->db->escape($this->fk_prospectlevel)."'";
  741. $sql .= ",webservices_url = ".(! empty($this->webservices_url)?"'".$this->db->escape($this->webservices_url)."'":"null");
  742. $sql .= ",webservices_key = ".(! empty($this->webservices_key)?"'".$this->db->escape($this->webservices_key)."'":"null");
  743. //Incoterms
  744. $sql.= ", fk_incoterms = ".$this->fk_incoterms;
  745. $sql.= ", location_incoterms = ".(! empty($this->location_incoterms)?"'".$this->db->escape($this->location_incoterms)."'":"null");
  746. if ($customer)
  747. {
  748. $sql .= ", code_client = ".(! empty($this->code_client)?"'".$this->db->escape($this->code_client)."'":"null");
  749. $sql .= ", code_compta = ".(! empty($this->code_compta)?"'".$this->db->escape($this->code_compta)."'":"null");
  750. }
  751. if ($supplier)
  752. {
  753. $sql .= ", code_fournisseur = ".(! empty($this->code_fournisseur)?"'".$this->db->escape($this->code_fournisseur)."'":"null");
  754. $sql .= ", code_compta_fournisseur = ".(! empty($this->code_compta_fournisseur)?"'".$this->db->escape($this->code_compta_fournisseur)."'":"null");
  755. }
  756. $sql .= ", fk_user_modif = ".(! empty($user->id)?"'".$user->id."'":"null");
  757. $sql .= ", fk_multicurrency = ".(int) $this->fk_multicurrency;
  758. $sql .= ', multicurrency_code = \''.$this->db->escape($this->multicurrency_code)."'";
  759. $sql .= " WHERE rowid = '" . $id ."'";
  760. dol_syslog(get_class($this)."::Update", LOG_DEBUG);
  761. $resql=$this->db->query($sql);
  762. if ($resql)
  763. {
  764. unset($this->country_code); // We clean this because it may have been changed after an update of country_id
  765. unset($this->country);
  766. unset($this->state_code);
  767. unset($this->state);
  768. $nbrowsaffected = $this->db->affected_rows($resql);
  769. if (! $error && $nbrowsaffected)
  770. {
  771. // Update information on linked member if it is an update
  772. if (! $nosyncmember && ! empty($conf->adherent->enabled))
  773. {
  774. require_once DOL_DOCUMENT_ROOT.'/adherents/class/adherent.class.php';
  775. dol_syslog(get_class($this)."::update update linked member");
  776. $lmember=new Adherent($this->db);
  777. $result=$lmember->fetch(0, 0, $this->id);
  778. if ($result > 0)
  779. {
  780. $lmember->societe=$this->name;
  781. //$lmember->firstname=$this->firstname?$this->firstname:$lmember->firstname; // We keep firstname and lastname of member unchanged
  782. //$lmember->lastname=$this->lastname?$this->lastname:$lmember->lastname; // We keep firstname and lastname of member unchanged
  783. $lmember->address=$this->address;
  784. $lmember->email=$this->email;
  785. $lmember->skype=$this->skype;
  786. $lmember->phone=$this->phone;
  787. $result=$lmember->update($user,0,1,1,1); // Use nosync to 1 to avoid cyclic updates
  788. if ($result < 0)
  789. {
  790. $this->error=$lmember->error;
  791. dol_syslog(get_class($this)."::update ".$this->error,LOG_ERR);
  792. $error++;
  793. }
  794. }
  795. else if ($result < 0)
  796. {
  797. $this->error=$lmember->error;
  798. $error++;
  799. }
  800. }
  801. }
  802. $action='update';
  803. // Actions on extra fields (by external module or standard code)
  804. // TODO le hook fait double emploi avec le trigger !!
  805. $hookmanager->initHooks(array('thirdpartydao'));
  806. $parameters=array('socid'=>$this->id);
  807. $reshook=$hookmanager->executeHooks('insertExtraFields',$parameters,$this,$action); // Note that $action and $object may have been modified by some hooks
  808. if (empty($reshook))
  809. {
  810. if (empty($conf->global->MAIN_EXTRAFIELDS_DISABLED)) // For avoid conflicts if trigger used
  811. {
  812. $result=$this->insertExtraFields();
  813. if ($result < 0)
  814. {
  815. $error++;
  816. }
  817. }
  818. }
  819. else if ($reshook < 0) $error++;
  820. if (! $error && $call_trigger)
  821. {
  822. // Call trigger
  823. $result=$this->call_trigger('COMPANY_MODIFY',$user);
  824. if ($result < 0) $error++;
  825. // End call triggers
  826. }
  827. if (! $error)
  828. {
  829. dol_syslog(get_class($this)."::Update success");
  830. $this->db->commit();
  831. return 1;
  832. }
  833. else
  834. {
  835. $this->db->rollback();
  836. return -1;
  837. }
  838. }
  839. else
  840. {
  841. if ($this->db->errno() == 'DB_ERROR_RECORD_ALREADY_EXISTS')
  842. {
  843. // Doublon
  844. $this->error = $langs->trans("ErrorDuplicateField");
  845. $result = -1;
  846. }
  847. else
  848. {
  849. $result = -2;
  850. }
  851. $this->db->rollback();
  852. return $result;
  853. }
  854. }
  855. else
  856. {
  857. $this->db->rollback();
  858. dol_syslog(get_class($this)."::Update fails verify ".join(',',$this->errors), LOG_WARNING);
  859. return -3;
  860. }
  861. }
  862. /**
  863. * Load a third party from database into memory
  864. *
  865. * @param int $rowid Id of third party to load
  866. * @param string $ref Reference of third party, name (Warning, this can return several records)
  867. * @param string $ref_ext External reference of third party (Warning, this information is a free field not provided by Dolibarr)
  868. * @param string $ref_int Internal reference of third party
  869. * @param string $idprof1 Prof id 1 of third party (Warning, this can return several records)
  870. * @param string $idprof2 Prof id 2 of third party (Warning, this can return several records)
  871. * @param string $idprof3 Prof id 3 of third party (Warning, this can return several records)
  872. * @param string $idprof4 Prof id 4 of third party (Warning, this can return several records)
  873. * @param string $idprof5 Prof id 5 of third party (Warning, this can return several records)
  874. * @param string $idprof6 Prof id 6 of third party (Warning, this can return several records)
  875. * @return int >0 if OK, <0 if KO or if two records found for same ref or idprof, 0 if not found.
  876. */
  877. function fetch($rowid, $ref='', $ref_ext='', $ref_int='', $idprof1='',$idprof2='',$idprof3='',$idprof4='',$idprof5='',$idprof6='')
  878. {
  879. global $langs;
  880. global $conf;
  881. if (empty($rowid) && empty($ref) && empty($ref_ext) && empty($ref_int) && empty($idprof1) && empty($idprof2) && empty($idprof3) && empty($idprof4) && empty($idprof5) && empty($idprof6)) return -1;
  882. $sql = 'SELECT s.rowid, s.nom as name, s.name_alias, s.entity, s.ref_ext, s.ref_int, s.address, s.datec as date_creation, s.prefix_comm';
  883. $sql .= ', s.status';
  884. $sql .= ', s.price_level';
  885. $sql .= ', s.tms as date_modification';
  886. $sql .= ', s.phone, s.fax, s.email, s.skype, s.url, s.zip, s.town, s.note_private, s.note_public, s.model_pdf, s.client, s.fournisseur';
  887. $sql .= ', s.siren as idprof1, s.siret as idprof2, s.ape as idprof3, s.idprof4, s.idprof5, s.idprof6';
  888. $sql .= ', s.capital, s.tva_intra';
  889. $sql .= ', s.fk_typent as typent_id';
  890. $sql .= ', s.fk_effectif as effectif_id';
  891. $sql .= ', s.fk_forme_juridique as forme_juridique_code';
  892. $sql .= ', s.webservices_url, s.webservices_key';
  893. $sql .= ', s.code_client, s.code_fournisseur, s.code_compta, s.code_compta_fournisseur, s.parent, s.barcode';
  894. $sql .= ', s.fk_departement, s.fk_pays as country_id, s.fk_stcomm, s.remise_client, s.mode_reglement, s.cond_reglement, s.fk_account, s.tva_assuj';
  895. $sql .= ', s.mode_reglement_supplier, s.cond_reglement_supplier, s.localtax1_assuj, s.localtax1_value, s.localtax2_assuj, s.localtax2_value, s.fk_prospectlevel, s.default_lang, s.logo';
  896. $sql .= ', s.fk_shipping_method';
  897. $sql .= ', s.outstanding_limit, s.import_key, s.canvas, s.fk_incoterms, s.location_incoterms';
  898. $sql .= ', s.fk_multicurrency, s.multicurrency_code';
  899. $sql .= ', fj.libelle as forme_juridique';
  900. $sql .= ', e.libelle as effectif';
  901. $sql .= ', c.code as country_code, c.label as country';
  902. $sql .= ', d.code_departement as state_code, d.nom as state';
  903. $sql .= ', st.libelle as stcomm';
  904. $sql .= ', te.code as typent_code';
  905. $sql .= ', i.libelle as libelle_incoterms';
  906. $sql .= ' FROM '.MAIN_DB_PREFIX.'societe as s';
  907. $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'c_effectif as e ON s.fk_effectif = e.id';
  908. $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'c_country as c ON s.fk_pays = c.rowid';
  909. $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'c_stcomm as st ON s.fk_stcomm = st.id';
  910. $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'c_forme_juridique as fj ON s.fk_forme_juridique = fj.code';
  911. $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'c_departements as d ON s.fk_departement = d.rowid';
  912. $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'c_typent as te ON s.fk_typent = te.id';
  913. $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'c_incoterms as i ON s.fk_incoterms = i.rowid';
  914. if ($rowid) $sql .= ' WHERE s.rowid = '.$rowid;
  915. else if ($ref) $sql .= " WHERE s.nom = '".$this->db->escape($ref)."' AND s.entity IN (".getEntity($this->element, 1).")";
  916. else if ($ref_ext) $sql .= " WHERE s.ref_ext = '".$this->db->escape($ref_ext)."' AND s.entity IN (".getEntity($this->element, 1).")";
  917. else if ($ref_int) $sql .= " WHERE s.ref_int = '".$this->db->escape($ref_int)."' AND s.entity IN (".getEntity($this->element, 1).")";
  918. else if ($idprof1) $sql .= " WHERE s.siren = '".$this->db->escape($idprof1)."' AND s.entity IN (".getEntity($this->element, 1).")";
  919. else if ($idprof2) $sql .= " WHERE s.siret = '".$this->db->escape($idprof2)."' AND s.entity IN (".getEntity($this->element, 1).")";
  920. else if ($idprof3) $sql .= " WHERE s.ape = '".$this->db->escape($idprof3)."' AND s.entity IN (".getEntity($this->element, 1).")";
  921. else if ($idprof4) $sql .= " WHERE s.idprof4 = '".$this->db->escape($idprof4)."' AND s.entity IN (".getEntity($this->element, 1).")";
  922. else if ($idprof5) $sql .= " WHERE s.idprof5 = '".$this->db->escape($idprof5)."' AND s.entity IN (".getEntity($this->element, 1).")";
  923. else if ($idprof6) $sql .= " WHERE s.idprof6 = '".$this->db->escape($idprof6)."' AND s.entity IN (".getEntity($this->element, 1).")";
  924. $resql=$this->db->query($sql);
  925. dol_syslog(get_class($this)."::fetch ".$sql);
  926. if ($resql)
  927. {
  928. $num=$this->db->num_rows($resql);
  929. if ($num > 1)
  930. {
  931. $this->error='Fetch found several records. Rename one of tirdparties to avoid duplicate.';
  932. dol_syslog($this->error, LOG_ERR);
  933. $result = -2;
  934. }
  935. elseif ($num) // $num = 1
  936. {
  937. $obj = $this->db->fetch_object($resql);
  938. $this->id = $obj->rowid;
  939. $this->entity = $obj->entity;
  940. $this->canvas = $obj->canvas;
  941. $this->ref = $obj->rowid;
  942. $this->name = $obj->name;
  943. $this->nom = $obj->name; // deprecated
  944. $this->name_alias = $obj->name_alias;
  945. $this->ref_ext = $obj->ref_ext;
  946. $this->ref_int = $obj->ref_int;
  947. $this->date_creation = $this->db->jdate($obj->date_creation);
  948. $this->date_modification = $this->db->jdate($obj->date_modification);
  949. $this->address = $obj->address;
  950. $this->zip = $obj->zip;
  951. $this->town = $obj->town;
  952. $this->country_id = $obj->country_id;
  953. $this->country_code = $obj->country_id?$obj->country_code:'';
  954. $this->country = $obj->country_id?($langs->trans('Country'.$obj->country_code)!='Country'.$obj->country_code?$langs->transnoentities('Country'.$obj->country_code):$obj->country):'';
  955. $this->state_id = $obj->fk_departement;
  956. $this->state_code = $obj->state_code;
  957. $this->state = ($obj->state!='-'?$obj->state:'');
  958. $transcode=$langs->trans('StatusProspect'.$obj->fk_stcomm);
  959. $libelle=($transcode!='StatusProspect'.$obj->fk_stcomm?$transcode:$obj->stcomm);
  960. $this->stcomm_id = $obj->fk_stcomm; // id statut commercial
  961. $this->statut_commercial = $libelle; // libelle statut commercial
  962. $this->email = $obj->email;
  963. $this->skype = $obj->skype;
  964. $this->url = $obj->url;
  965. $this->phone = $obj->phone;
  966. $this->fax = $obj->fax;
  967. $this->parent = $obj->parent;
  968. $this->idprof1 = $obj->idprof1;
  969. $this->idprof2 = $obj->idprof2;
  970. $this->idprof3 = $obj->idprof3;
  971. $this->idprof4 = $obj->idprof4;
  972. $this->idprof5 = $obj->idprof5;
  973. $this->idprof6 = $obj->idprof6;
  974. $this->capital = $obj->capital;
  975. $this->code_client = $obj->code_client;
  976. $this->code_fournisseur = $obj->code_fournisseur;
  977. $this->code_compta = $obj->code_compta;
  978. $this->code_compta_fournisseur = $obj->code_compta_fournisseur;
  979. $this->barcode = $obj->barcode;
  980. $this->tva_assuj = $obj->tva_assuj;
  981. $this->tva_intra = $obj->tva_intra;
  982. $this->status = $obj->status;
  983. // Local Taxes
  984. $this->localtax1_assuj = $obj->localtax1_assuj;
  985. $this->localtax2_assuj = $obj->localtax2_assuj;
  986. $this->localtax1_value = $obj->localtax1_value;
  987. $this->localtax2_value = $obj->localtax2_value;
  988. $this->typent_id = $obj->typent_id;
  989. $this->typent_code = $obj->typent_code;
  990. $this->effectif_id = $obj->effectif_id;
  991. $this->effectif = $obj->effectif_id?$obj->effectif:'';
  992. $this->forme_juridique_code= $obj->forme_juridique_code;
  993. $this->forme_juridique = $obj->forme_juridique_code?$obj->forme_juridique:'';
  994. $this->fk_prospectlevel = $obj->fk_prospectlevel;
  995. $this->prefix_comm = $obj->prefix_comm;
  996. $this->remise_percent = $obj->remise_client;
  997. $this->mode_reglement_id = $obj->mode_reglement;
  998. $this->cond_reglement_id = $obj->cond_reglement;
  999. $this->mode_reglement_supplier_id = $obj->mode_reglement_supplier;
  1000. $this->cond_reglement_supplier_id = $obj->cond_reglement_supplier;
  1001. $this->shipping_method_id = ($obj->fk_shipping_method>0)?$obj->fk_shipping_method:null;
  1002. $this->fk_account = $obj->fk_account;
  1003. $this->client = $obj->client;
  1004. $this->fournisseur = $obj->fournisseur;
  1005. $this->note = $obj->note_private; // TODO Deprecated for backward comtability
  1006. $this->note_private = $obj->note_private;
  1007. $this->note_public = $obj->note_public;
  1008. $this->modelpdf = $obj->model_pdf;
  1009. $this->default_lang = $obj->default_lang;
  1010. $this->logo = $obj->logo;
  1011. $this->webservices_url = $obj->webservices_url;
  1012. $this->webservices_key = $obj->webservices_key;
  1013. $this->outstanding_limit = $obj->outstanding_limit;
  1014. // multiprix
  1015. $this->price_level = $obj->price_level;
  1016. $this->import_key = $obj->import_key;
  1017. //Incoterms
  1018. $this->fk_incoterms = $obj->fk_incoterms;
  1019. $this->location_incoterms = $obj->location_incoterms;
  1020. $this->libelle_incoterms = $obj->libelle_incoterms;
  1021. // multicurrency
  1022. $this->fk_multicurrency = $obj->fk_multicurrency;
  1023. $this->multicurrency_code = $obj->multicurrency_code;
  1024. $result = 1;
  1025. // Retreive all extrafield for thirdparty
  1026. // fetch optionals attributes and labels
  1027. require_once(DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php');
  1028. $extrafields=new ExtraFields($this->db);
  1029. $extralabels=$extrafields->fetch_name_optionals_label($this->table_element,true);
  1030. $this->fetch_optionals($this->id,$extralabels);
  1031. }
  1032. else
  1033. {
  1034. $result = 0;
  1035. }
  1036. $this->db->free($resql);
  1037. }
  1038. else
  1039. {
  1040. $this->error=$this->db->lasterror();
  1041. $result = -3;
  1042. }
  1043. // Use first price level if level not defined for third party
  1044. if (! empty($conf->global->PRODUIT_MULTIPRICES) && empty($this->price_level)) $this->price_level=1;
  1045. return $result;
  1046. }
  1047. /**
  1048. * Search and fetch thirparties by name
  1049. *
  1050. * @param string $name Name
  1051. * @param int $type Type of thirdparties (0=any, 1=customer, 2=prospect, 3=supplier)
  1052. * @param array $filters Array of couple field name/value to filter the companies with the same name
  1053. * @param boolean $exact Exact string search (true/false)
  1054. * @param boolean $case Case sensitive (true/false)
  1055. * @param boolean $similar Add test if string inside name into database, or name into database inside string. Do not use this: Not compatible with other database.
  1056. * @param string $clause Clause for filters
  1057. * @return array|int <0 if KO, array of thirdparties object if OK
  1058. */
  1059. function searchByName($name, $type='0', $filters = array(), $exact = false, $case = false, $similar = false, $clause = 'AND')
  1060. {
  1061. $thirdparties = array();
  1062. dol_syslog("searchByName name=".$name." type=".$type." exact=".$exact);
  1063. // Check parameter
  1064. if (empty($name))
  1065. {
  1066. $this->errors[]='ErrorBadValueForParameter';
  1067. return -1;
  1068. }
  1069. // Generation requete recherche
  1070. $sql = "SELECT rowid FROM ".MAIN_DB_PREFIX."societe";
  1071. $sql.= " WHERE entity IN (".getEntity('category',1).")";
  1072. if (! empty($type))
  1073. {
  1074. if ($type == 1 || $type == 2)
  1075. $sql.= " AND client = ".$type;
  1076. elseif ($type == 3)
  1077. $sql.= " AND fournisseur = 1";
  1078. }
  1079. if (! empty($name))
  1080. {
  1081. if (! $exact)
  1082. {
  1083. if (preg_match('/^([\*])?[^*]+([\*])?$/', $name, $regs) && count($regs) > 1)
  1084. {
  1085. $name = str_replace('*', '%', $name);
  1086. }
  1087. else
  1088. {
  1089. $name = '%'.$name.'%';
  1090. }
  1091. }
  1092. $sql.= " AND ";
  1093. if (is_array($filters) && ! empty($filters))
  1094. $sql.= "(";
  1095. if ($similar)
  1096. {
  1097. // For test similitude (string inside name into database, or name into database inside string)
  1098. // Do not use this. Not compatible with other database.
  1099. $sql.= "(LOCATE('".$this->db->escape($name)."', nom) > 0 OR LOCATE(nom, '".$this->db->escape($name)."') > 0)";
  1100. }
  1101. else
  1102. {
  1103. if (! $case)
  1104. $sql.= "nom LIKE '".$this->db->escape($name)."'";
  1105. else
  1106. $sql.= "nom LIKE BINARY '".$this->db->escape($name)."'";
  1107. }
  1108. }
  1109. if (is_array($filters) && ! empty($filters))
  1110. {
  1111. foreach($filters as $field => $value)
  1112. {
  1113. if (! $exact)
  1114. {
  1115. if (preg_match('/^([\*])?[^*]+([\*])?$/', $value, $regs) && count($regs) > 1)
  1116. {
  1117. $value = str_replace('*', '%', $value);
  1118. }
  1119. else
  1120. {
  1121. $value = '%'.$value.'%';
  1122. }
  1123. }
  1124. if (! $case)
  1125. $sql.= " ".$clause." ".$field." LIKE '".$this->db->escape($value)."'";
  1126. else
  1127. $sql.= " ".$clause." ".$field." LIKE BINARY '".$this->db->escape($value)."'";
  1128. }
  1129. if (! empty($name))
  1130. $sql.= ")";
  1131. }
  1132. $res = $this->db->query($sql);
  1133. if ($res)
  1134. {
  1135. while ($rec = $this->db->fetch_array($res))
  1136. {
  1137. $soc = new Societe($this->db);
  1138. $soc->fetch($rec['rowid']);
  1139. $thirdparties[] = $soc;
  1140. }
  1141. return $thirdparties;
  1142. }
  1143. else
  1144. {
  1145. $this->error=$this->db->lasterror();
  1146. return -1;
  1147. }
  1148. }
  1149. /**
  1150. * Delete a third party from database and all its dependencies (contacts, rib...)
  1151. *
  1152. * @param int $id Id of third party to delete
  1153. * @param User $fuser User who ask to delete thirparty
  1154. * @param int $call_trigger 0=No, 1=yes
  1155. * @return int <0 if KO, 0 if nothing done, >0 if OK
  1156. */
  1157. function delete($id, User $fuser=null, $call_trigger=1)
  1158. {
  1159. global $langs, $conf, $user;
  1160. if (empty($fuser)) $fuser=$user;
  1161. require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
  1162. $entity=isset($this->entity)?$this->entity:$conf->entity;
  1163. dol_syslog(get_class($this)."::delete", LOG_DEBUG);
  1164. $error = 0;
  1165. // Test if child exists
  1166. $objectisused = $this->isObjectUsed($id);
  1167. if (empty($objectisused))
  1168. {
  1169. $this->db->begin();
  1170. // User is mandatory for trigger call
  1171. if (! $error && $call_trigger)
  1172. {
  1173. // Call trigger
  1174. $result=$this->call_trigger('COMPANY_DELETE',$fuser);
  1175. if ($result < 0) $error++;
  1176. // End call triggers
  1177. }
  1178. if (! $error)
  1179. {
  1180. require_once DOL_DOCUMENT_ROOT.'/categories/class/categorie.class.php';
  1181. $static_cat = new Categorie($this->db);
  1182. $toute_categs = array();
  1183. // Fill $toute_categs array with an array of (type => array of ("Categorie" instance))
  1184. if ($this->client || $this->prospect)
  1185. {
  1186. $toute_categs ['societe'] = $static_cat->containing($this->id,Categorie::TYPE_CUSTOMER);
  1187. }
  1188. if ($this->fournisseur)
  1189. {
  1190. $toute_categs ['fournisseur'] = $static_cat->containing($this->id,Categorie::TYPE_SUPPLIER);
  1191. }
  1192. // Remove each "Categorie"
  1193. foreach ($toute_categs as $type => $categs_type)
  1194. {
  1195. foreach ($categs_type as $cat)
  1196. {
  1197. $cat->del_type($this, $type);
  1198. }
  1199. }
  1200. }
  1201. // Remove contacts
  1202. if (! $error)
  1203. {
  1204. $sql = "DELETE FROM ".MAIN_DB_PREFIX."socpeople";
  1205. $sql.= " WHERE fk_soc = " . $id;
  1206. if (! $this->db->query($sql))
  1207. {
  1208. $error++;
  1209. $this->error .= $this->db->lasterror();
  1210. }
  1211. }
  1212. // Update link in member table
  1213. if (! $error)
  1214. {
  1215. $sql = "UPDATE ".MAIN_DB_PREFIX."adherent";
  1216. $sql.= " SET fk_soc = NULL WHERE fk_soc = " . $id;
  1217. if (! $this->db->query($sql))
  1218. {
  1219. $error++;
  1220. $this->error .= $this->db->lasterror();
  1221. dol_syslog(get_class($this)."::delete erreur -1 ".$this->error, LOG_ERR);
  1222. }
  1223. }
  1224. // Remove ban
  1225. if (! $error)
  1226. {
  1227. $sql = "DELETE FROM ".MAIN_DB_PREFIX."societe_rib";
  1228. $sql.= " WHERE fk_soc = " . $id;
  1229. if (! $this->db->query($sql))
  1230. {
  1231. $error++;
  1232. $this->error = $this->db->lasterror();
  1233. }
  1234. }
  1235. // Remove societe_remise
  1236. if (! $error)
  1237. {
  1238. $sql = "DELETE FROM ".MAIN_DB_PREFIX."societe_remise";
  1239. $sql.= " WHERE fk_soc = " . $id;
  1240. if (! $this->db->query($sql))
  1241. {
  1242. $error++;
  1243. $this->error = $this->db->lasterror();
  1244. }
  1245. }
  1246. // Remove societe_remise_except
  1247. if (! $error)
  1248. {
  1249. $sql = "DELETE FROM ".MAIN_DB_PREFIX."societe_remise_except";
  1250. $sql.= " WHERE fk_soc = " . $id;
  1251. if (! $this->db->query($sql))
  1252. {
  1253. $error++;
  1254. $this->error = $this->db->lasterror();
  1255. }
  1256. }
  1257. // Remove associated users
  1258. if (! $error)
  1259. {
  1260. $sql = "DELETE FROM ".MAIN_DB_PREFIX."societe_commerciaux";
  1261. $sql.= " WHERE fk_soc = " . $id;
  1262. if (! $this->db->query($sql))
  1263. {
  1264. $error++;
  1265. $this->error = $this->db->lasterror();
  1266. }
  1267. }
  1268. // Removed extrafields
  1269. if ((! $error) && (empty($conf->global->MAIN_EXTRAFIELDS_DISABLED))) // For avoid conflicts if trigger used
  1270. {
  1271. $result=$this->deleteExtraFields();
  1272. if ($result < 0)
  1273. {
  1274. $error++;
  1275. dol_syslog(get_class($this)."::delete error -3 ".$this->error, LOG_ERR);
  1276. }
  1277. }
  1278. // Remove third party
  1279. if (! $error)
  1280. {
  1281. $sql = "DELETE FROM ".MAIN_DB_PREFIX."societe";
  1282. $sql.= " WHERE rowid = " . $id;
  1283. dol_syslog(get_class($this)."::delete", LOG_DEBUG);
  1284. if (! $this->db->query($sql))
  1285. {
  1286. $error++;
  1287. $this->error = $this->db->lasterror();
  1288. }
  1289. }
  1290. if (! $error)
  1291. {
  1292. $this->db->commit();
  1293. // Delete directory
  1294. if (! empty($conf->societe->multidir_output[$entity]))
  1295. {
  1296. $docdir = $conf->societe->multidir_output[$entity] . "/" . $id;
  1297. if (dol_is_dir($docdir))
  1298. {
  1299. dol_delete_dir_recursive($docdir);
  1300. }
  1301. }
  1302. return 1;
  1303. }
  1304. else
  1305. {
  1306. dol_syslog($this->error, LOG_ERR);
  1307. $this->db->rollback();
  1308. return -1;
  1309. }
  1310. }
  1311. else dol_syslog("Can't remove thirdparty with id ".$id.". There is ".$objectisused." childs", LOG_WARNING);
  1312. return 0;
  1313. }
  1314. /**
  1315. * Define third party as a customer
  1316. *
  1317. * @return int <0 if KO, >0 if OK
  1318. */
  1319. function set_as_client()
  1320. {
  1321. if ($this->id)
  1322. {
  1323. $newclient=1;
  1324. if ($this->client == 2 || $this->client == 3) $newclient=3; //If prospect, we keep prospect tag
  1325. $sql = "UPDATE ".MAIN_DB_PREFIX."societe";
  1326. $sql.= " SET client = ".$newclient;
  1327. $sql.= " WHERE rowid = " . $this->id;
  1328. $resql=$this->db->query($sql);
  1329. if ($resql)
  1330. {
  1331. $this->client = $newclient;
  1332. return 1;
  1333. }
  1334. else return -1;
  1335. }
  1336. return 0;
  1337. }
  1338. /**
  1339. * Definit la societe comme un client
  1340. *
  1341. * @param float $remise Valeur en % de la remise
  1342. * @param string $note Note/Motif de modification de la remise
  1343. * @param User $user Utilisateur qui definie la remise
  1344. * @return int <0 if KO, >0 if OK
  1345. */
  1346. function set_remise_client($remise, $note, User $user)
  1347. {
  1348. global $conf, $langs;
  1349. // Nettoyage parametres
  1350. $note=trim($note);
  1351. if (! $note)
  1352. {
  1353. $this->error=$langs->trans("ErrorFieldRequired",$langs->trans("NoteReason"));
  1354. return -2;
  1355. }
  1356. dol_syslog(get_class($this)."::set_remise_client ".$remise.", ".$note.", ".$user->id);
  1357. if ($this->id)
  1358. {
  1359. $this->db->begin();
  1360. $now=dol_now();
  1361. // Positionne remise courante
  1362. $sql = "UPDATE ".MAIN_DB_PREFIX."societe ";
  1363. $sql.= " SET remise_client = '".$this->db->escape($remise)."'";
  1364. $sql.= " WHERE rowid = " . $this->id .";";
  1365. $resql=$this->db->query($sql);
  1366. if (! $resql)
  1367. {
  1368. $this->db->rollback();
  1369. $this->error=$this->db->error();
  1370. return -1;
  1371. }
  1372. // Ecrit trace dans historique des remises
  1373. $sql = "INSERT INTO ".MAIN_DB_PREFIX."societe_remise";
  1374. $sql.= " (entity, datec, fk_soc, remise_client, note, fk_user_author)";
  1375. $sql.= " VALUES (".$conf->entity.", '".$this->db->idate($now)."', ".$this->id.", '".$this->db->escape($remise)."',";
  1376. $sql.= " '".$this->db->escape($note)."',";
  1377. $sql.= " ".$user->id;
  1378. $sql.= ")";
  1379. $resql=$this->db->query($sql);
  1380. if (! $resql)
  1381. {
  1382. $this->db->rollback();
  1383. $this->error=$this->db->lasterror();
  1384. return -1;
  1385. }
  1386. $this->db->commit();
  1387. return 1;
  1388. }
  1389. }
  1390. /**
  1391. * Add a discount for third party
  1392. *
  1393. * @param float $remise Amount of discount
  1394. * @param User $user User adding discount
  1395. * @param string $desc Reason of discount
  1396. * @param float $tva_tx VAT rate
  1397. * @return int <0 if KO, id of discount record if OK
  1398. */
  1399. function set_remise_except($remise, User $user, $desc, $tva_tx=0)
  1400. {
  1401. global $langs;
  1402. // Clean parameters
  1403. $remise = price2num($remise);
  1404. $desc = trim($desc);
  1405. // Check parameters
  1406. if (! $remise > 0)
  1407. {
  1408. $this->error=$langs->trans("ErrorWrongValueForParameter","1");
  1409. return -1;
  1410. }
  1411. if (! $desc)
  1412. {
  1413. $this->error=$langs->trans("ErrorWrongValueForParameter","3");
  1414. return -2;
  1415. }
  1416. if ($this->id)
  1417. {
  1418. require_once DOL_DOCUMENT_ROOT.'/core/class/discount.class.php';
  1419. $discount = new DiscountAbsolute($this->db);
  1420. $discount->fk_soc=$this->id;
  1421. $discount->amount_ht=price2num($remise,'MT');
  1422. $discount->amount_tva=price2num($remise*$tva_tx/100,'MT');
  1423. $discount->amount_ttc=price2num($discount->amount_ht+$discount->amount_tva,'MT');
  1424. $discount->tva_tx=price2num($tva_tx,'MT');
  1425. $discount->description=$desc;
  1426. $result=$discount->create($user);
  1427. if ($result > 0)
  1428. {
  1429. return $result;
  1430. }
  1431. else
  1432. {
  1433. $this->error=$discount->error;
  1434. return -3;
  1435. }
  1436. }
  1437. else return 0;
  1438. }
  1439. /**
  1440. * Renvoie montant TTC des reductions/avoirs en cours disponibles de la societe
  1441. *
  1442. * @param User $user Filtre sur un user auteur des remises
  1443. * @param string $filter Filtre autre
  1444. * @param integer $maxvalue Filter on max value for discount
  1445. * @return int <0 if KO, Credit note amount otherwise
  1446. */
  1447. function getAvailableDiscounts($user='',$filter='',$maxvalue=0)
  1448. {
  1449. require_once DOL_DOCUMENT_ROOT.'/core/class/discount.class.php';
  1450. $discountstatic=new DiscountAbsolute($this->db);
  1451. $result=$discountstatic->getAvailableDiscounts($this,$user,$filter,$maxvalue);
  1452. if ($result >= 0)
  1453. {
  1454. return $result;
  1455. }
  1456. else
  1457. {
  1458. $this->error=$discountstatic->error;
  1459. return -1;
  1460. }
  1461. }
  1462. /**
  1463. * Return array of sales representatives
  1464. *
  1465. * @param User $user Object user
  1466. * @return array Array of sales representatives of third party
  1467. */
  1468. function getSalesRepresentatives(User $user)
  1469. {
  1470. global $conf;
  1471. $reparray=array();
  1472. $sql = "SELECT DISTINCT u.rowid, u.login, u.lastname, u.firstname, u.email, u.statut, u.entity, u.photo";
  1473. $sql.= " FROM ".MAIN_DB_PREFIX."societe_commerciaux as sc, ".MAIN_DB_PREFIX."user as u";
  1474. if (! empty($conf->multicompany->enabled) && ! empty($conf->multicompany->transverse_mode))
  1475. {
  1476. $sql.= ", ".MAIN_DB_PREFIX."usergroup_user as ug";
  1477. $sql.= " WHERE ((ug.fk_user = sc.fk_user";
  1478. $sql.= " AND ug.entity = ".$conf->entity.")";
  1479. $sql.= " OR u.admin = 1)";
  1480. }
  1481. else
  1482. $sql.= " WHERE entity in (0, ".$conf->entity.")";
  1483. $sql.= " AND u.rowid = sc.fk_user AND sc.fk_soc =".$this->id;
  1484. $resql = $this->db->query($sql);
  1485. if ($resql)
  1486. {
  1487. $num = $this->db->num_rows($resql);
  1488. $i=0;
  1489. while ($i < $num)
  1490. {
  1491. $obj = $this->db->fetch_object($resql);
  1492. $reparray[$i]['id']=$obj->rowid;
  1493. $reparray[$i]['lastname']=$obj->lastname;
  1494. $reparray[$i]['firstname']=$obj->firstname;
  1495. $reparray[$i]['email']=$obj->email;
  1496. $reparray[$i]['statut']=$obj->statut;
  1497. $reparray[$i]['entity']=$obj->entity;
  1498. $reparray[$i]['login']=$obj->login;
  1499. $reparray[$i]['photo']=$obj->photo;
  1500. $i++;
  1501. }
  1502. return $reparray;
  1503. }
  1504. else {
  1505. dol_print_error($this->db);
  1506. return -1;
  1507. }
  1508. }
  1509. /**
  1510. * Set the price level
  1511. *
  1512. * @param int $price_level Level of price
  1513. * @param User $user Use making change
  1514. * @return int <0 if KO, >0 if OK
  1515. */
  1516. function set_price_level($price_level, User $user)
  1517. {
  1518. if ($this->id)
  1519. {
  1520. $now=dol_now();
  1521. $sql = "UPDATE ".MAIN_DB_PREFIX."societe";
  1522. $sql .= " SET price_level = '".$this->db->escape($price_level)."'";
  1523. $sql .= " WHERE rowid = " . $this->id;
  1524. if (! $this->db->query($sql))
  1525. {
  1526. dol_print_error($this->db);
  1527. return -1;
  1528. }
  1529. $sql = "INSERT INTO ".MAIN_DB_PREFIX."societe_prices";
  1530. $sql .= " (datec, fk_soc, price_level, fk_user_author)";
  1531. $sql .= " VALUES ('".$this->db->idate($now)."',".$this->id.",'".$this->db->escape($price_level)."',".$user->id.")";
  1532. if (! $this->db->query($sql))
  1533. {
  1534. dol_print_error($this->db);
  1535. return -1;
  1536. }
  1537. return 1;
  1538. }
  1539. return -1;
  1540. }
  1541. /**
  1542. * Add link to sales representative
  1543. *
  1544. * @param User $user Object user
  1545. * @param int $commid Id of user
  1546. * @return void
  1547. */
  1548. function add_commercial(User $user, $commid)
  1549. {
  1550. if ($this->id > 0 && $commid > 0)
  1551. {
  1552. $sql = "DELETE FROM ".MAIN_DB_PREFIX."societe_commerciaux";
  1553. $sql.= " WHERE fk_soc = ".$this->id." AND fk_user =".$commid;
  1554. $this->db->query($sql);
  1555. $sql = "INSERT INTO ".MAIN_DB_PREFIX."societe_commerciaux";
  1556. $sql.= " ( fk_soc, fk_user )";
  1557. $sql.= " VALUES (".$this->id.",".$commid.")";
  1558. if (! $this->db->query($sql) )
  1559. {
  1560. dol_syslog(get_class($this)."::add_commercial Erreur");
  1561. }
  1562. }
  1563. }
  1564. /**
  1565. * Add link to sales representative
  1566. *
  1567. * @param User $user Object user
  1568. * @param int $commid Id of user
  1569. * @return void
  1570. */
  1571. function del_commercial(User $user, $commid)
  1572. {
  1573. if ($this->id > 0 && $commid > 0)
  1574. {
  1575. $sql = "DELETE FROM ".MAIN_DB_PREFIX."societe_commerciaux ";
  1576. $sql .= " WHERE fk_soc = ".$this->id." AND fk_user =".$commid;
  1577. if (! $this->db->query($sql) )
  1578. {
  1579. dol_syslog(get_class($this)."::del_commercial Erreur");
  1580. }
  1581. }
  1582. }
  1583. /**
  1584. * Return a link on thirdparty (with picto)
  1585. *
  1586. * @param int $withpicto Add picto into link (0=No picto, 1=Include picto with link, 2=Picto only)
  1587. * @param string $option Target of link ('', 'customer', 'prospect', 'supplier', 'project')
  1588. * @param int $maxlen Max length of name
  1589. * @param int $notooltip 1=Disable tooltip
  1590. * @param int $save_lastsearch_value -1=Auto, 0=No save of lastsearch_values when clicking, 1=Save lastsearch_values whenclicking
  1591. * @return string String with URL
  1592. */
  1593. function getNomUrl($withpicto=0, $option='', $maxlen=0, $notooltip=0, $save_lastsearch_value=-1)
  1594. {
  1595. global $conf, $langs, $hookmanager;
  1596. if (! empty($conf->dol_no_mouse_hover)) $notooltip=1; // Force disable tooltips
  1597. $name=$this->name?$this->name:$this->nom;
  1598. if (! empty($conf->global->SOCIETE_ADD_REF_IN_LIST) && (!empty($withpicto)))
  1599. {
  1600. if (($this->client) && (! empty ( $this->code_client ))
  1601. && ($conf->global->SOCIETE_ADD_REF_IN_LIST == 1
  1602. || $conf->global->SOCIETE_ADD_REF_IN_LIST == 2
  1603. )
  1604. )
  1605. $code = $this->code_client . ' - ';
  1606. if (($this->fournisseur) && (! empty ( $this->code_fournisseur ))
  1607. && ($conf->global->SOCIETE_ADD_REF_IN_LIST == 1
  1608. || $conf->global->SOCIETE_ADD_REF_IN_LIST == 3
  1609. )
  1610. )
  1611. $code .= $this->code_fournisseur . ' - ';
  1612. if ($conf->global->SOCIETE_ADD_REF_IN_LIST == 1)
  1613. $name =$code.' '.$name;
  1614. else
  1615. $name =$code;
  1616. }
  1617. if (!empty($this->name_alias)) $name .= ' ('.$this->name_alias.')';
  1618. $result=''; $label='';
  1619. $linkstart=''; $linkend='';
  1620. if (! empty($this->logo) && class_exists('Form'))
  1621. {
  1622. $label.= '<div class="photointooltip">';
  1623. $label.= Form::showphoto('societe', $this, 80, 0, 0, 'photowithmargin', 'mini');
  1624. $label.= '</div><div style="clear: both;"></div>';
  1625. }
  1626. $label.= '<div class="centpercent">';
  1627. if ($option == 'customer' || $option == 'compta' || $option == 'category' || $option == 'category_supplier')
  1628. {
  1629. $label.= '<u>' . $langs->trans("ShowCustomer") . '</u>';
  1630. $linkstart = '<a href="'.DOL_URL_ROOT.'/comm/card.php?socid='.$this->id;
  1631. }
  1632. else if ($option == 'prospect' && empty($conf->global->SOCIETE_DISABLE_PROSPECTS))
  1633. {
  1634. $label.= '<u>' . $langs->trans("ShowProspect") . '</u>';
  1635. $linkstart = '<a href="'.DOL_URL_ROOT.'/comm/card.php?socid='.$this->id;
  1636. }
  1637. else if ($option == 'supplier')
  1638. {
  1639. $label.= '<u>' . $langs->trans("ShowSupplier") . '</u>';
  1640. $linkstart = '<a href="'.DOL_URL_ROOT.'/fourn/card.php?socid='.$this->id;
  1641. }
  1642. else if ($option == 'agenda')
  1643. {
  1644. $label.= '<u>' . $langs->trans("ShowAgenda") . '</u>';
  1645. $linkstart = '<a href="'.DOL_URL_ROOT.'/societe/agenda.php?socid='.$this->id;
  1646. }
  1647. else if ($option == 'project')
  1648. {
  1649. $label.= '<u>' . $langs->trans("ShowProject") . '</u>';
  1650. $linkstart = '<a href="'.DOL_URL_ROOT.'/societe/project.php?socid='.$this->id;
  1651. }
  1652. else if ($option == 'margin')
  1653. {
  1654. $label.= '<u>' . $langs->trans("ShowMargin") . '</u>';
  1655. $linkstart = '<a href="'.DOL_URL_ROOT.'/margin/tabs/thirdpartyMargins.php?socid='.$this->id.'&type=1';
  1656. }
  1657. // By default
  1658. if (empty($linkstart))
  1659. {
  1660. $label.= '<u>' . $langs->trans("ShowCompany") . '</u>';
  1661. $linkstart = '<a href="'.DOL_URL_ROOT.'/societe/card.php?socid='.$this->id;
  1662. }
  1663. if (! empty($this->name))
  1664. {
  1665. $label.= '<br><b>' . $langs->trans('Name') . ':</b> '. $this->name;
  1666. if (! empty($this->name_alias)) $label.=' ('.$this->name_alias.')';
  1667. }
  1668. if (! empty($this->code_client) && $this->client)
  1669. $label.= '<br><b>' . $langs->trans('CustomerCode') . ':</b> '. $this->code_client;
  1670. if (! empty($this->code_fournisseur) && $this->fournisseur)
  1671. $label.= '<br><b>' . $langs->trans('SupplierCode') . ':</b> '. $this->code_fournisseur;
  1672. if (! empty($conf->accounting->enabled) && $this->client)
  1673. $label.= '<br><b>' . $langs->trans('CustomerAccountancyCode') . ':</b> '. $this->code_compta_client;
  1674. if (! empty($conf->accounting->enabled) && $this->fournisseur)
  1675. $label.= '<br><b>' . $langs->trans('SupplierAccountancyCode') . ':</b> '. $this->code_compta_fournisseur;
  1676. $label.= '</div>';
  1677. // Add type of canvas
  1678. $linkstart.=(!empty($this->canvas)?'&canvas='.$this->canvas:'');
  1679. // Add param to save lastsearch_values or not
  1680. $add_save_lastsearch_values=($save_lastsearch_value == 1 ? 1 : 0);
  1681. if ($save_lastsearch_value == -1 && preg_match('/list\.php/',$_SERVER["PHP_SELF"])) $add_save_lastsearch_values=1;
  1682. if ($add_save_lastsearch_values) $linkstart.='&save_lastsearch_values=1';
  1683. $linkstart.='"';
  1684. $linkclose='';
  1685. if (empty($notooltip))
  1686. {
  1687. if (! empty($conf->global->MAIN_OPTIMIZEFORTEXTBROWSER))
  1688. {
  1689. $label=$langs->trans("ShowCompany");
  1690. $linkclose.=' alt="'.dol_escape_htmltag($label, 1).'"';
  1691. }
  1692. $linkclose.= ' title="'.dol_escape_htmltag($label, 1).'"';
  1693. $linkclose.=' class="classfortooltip"';
  1694. if (! is_object($hookmanager))
  1695. {
  1696. include_once DOL_DOCUMENT_ROOT.'/core/class/hookmanager.class.php';
  1697. $hookmanager=new HookManager($this->db);
  1698. }
  1699. $hookmanager->initHooks(array('societedao'));
  1700. $parameters=array('id'=>$this->id);
  1701. $reshook=$hookmanager->executeHooks('getnomurltooltip',$parameters,$this,$action); // Note that $action and $object may have been modified by some hooks
  1702. if ($reshook > 0) $linkclose = $hookmanager->resPrint;
  1703. }
  1704. $linkstart.=$linkclose.'>';
  1705. $linkend='</a>';
  1706. global $user;
  1707. if (! $user->rights->societe->client->voir && $user->societe_id > 0 && $this->id != $user->societe_id)
  1708. {
  1709. $linkstart='';
  1710. $linkend='';
  1711. }
  1712. if ($withpicto) $result.=($linkstart.img_object(($notooltip?'':$label), 'company', ($notooltip?'':'class="classfortooltip valigntextbottom"'), 0, 0, $notooltip?0:1).$linkend);
  1713. if ($withpicto && $withpicto != 2) $result.=' ';
  1714. if ($withpicto != 2) $result.=$linkstart.($maxlen?dol_trunc($name,$maxlen):$name).$linkend;
  1715. return $result;
  1716. }
  1717. /**
  1718. * Return label of status (activity, closed)
  1719. *
  1720. * @param int $mode 0=libelle long, 1=libelle court, 2=Picto + Libelle court, 3=Picto, 4=Picto + Libelle long
  1721. * @return string Libelle
  1722. */
  1723. function getLibStatut($mode=0)
  1724. {
  1725. return $this->LibStatut($this->status,$mode);
  1726. }
  1727. /**
  1728. * Renvoi le libelle d'un statut donne
  1729. *
  1730. * @param int $statut Id statut
  1731. * @param int $mode 0=libelle long, 1=libelle court, 2=Picto + Libelle court, 3=Picto, 4=Picto + Libelle long, 5=Libelle court + Picto
  1732. * @return string Libelle du statut
  1733. */
  1734. function LibStatut($statut,$mode=0)
  1735. {
  1736. global $langs;
  1737. $langs->load('companies');
  1738. if ($mode == 0)
  1739. {
  1740. if ($statut==0) return $langs->trans("ActivityCeased");
  1741. if ($statut==1) return $langs->trans("InActivity");
  1742. }
  1743. if ($mode == 1)
  1744. {
  1745. if ($statut==0) return $langs->trans("ActivityCeased");
  1746. if ($statut==1) return $langs->trans("InActivity");
  1747. }
  1748. if ($mode == 2)
  1749. {
  1750. if ($statut==0) return img_picto($langs->trans("ActivityCeased"),'statut5', 'class="pictostatus"').' '.$langs->trans("ActivityCeased");
  1751. if ($statut==1) return img_picto($langs->trans("InActivity"),'statut4', 'class="pictostatus"').' '.$langs->trans("InActivity");
  1752. }
  1753. if ($mode == 3)
  1754. {
  1755. if ($statut==0) return img_picto($langs->trans("ActivityCeased"),'statut5', 'class="pictostatus"');
  1756. if ($statut==1) return img_picto($langs->trans("InActivity"),'statut4', 'class="pictostatus"');
  1757. }
  1758. if ($mode == 4)
  1759. {
  1760. if ($statut==0) return img_picto($langs->trans("ActivityCeased"),'statut5', 'class="pictostatus"').' '.$langs->trans("ActivityCeased");
  1761. if ($statut==1) return img_picto($langs->trans("InActivity"),'statut4', 'class="pictostatus"').' '.$langs->trans("InActivity");
  1762. }
  1763. if ($mode == 5)
  1764. {
  1765. if ($statut==0) return $langs->trans("ActivityCeased").' '.img_picto($langs->trans("ActivityCeased"),'statut5', 'class="pictostatus"');
  1766. if ($statut==1) return $langs->trans("InActivity").' '.img_picto($langs->trans("InActivity"),'statut4', 'class="pictostatus"');
  1767. }
  1768. }
  1769. /**
  1770. * Return list of contacts emails existing for third party
  1771. *
  1772. * @param int $addthirdparty 1=Add also a record for thirdparty email
  1773. * @return array Array of contacts emails
  1774. */
  1775. function thirdparty_and_contact_email_array($addthirdparty=0)
  1776. {
  1777. global $langs;
  1778. $contact_emails = $this->contact_property_array('email',1);
  1779. if ($this->email && $addthirdparty)
  1780. {
  1781. if (empty($this->name)) $this->name=$this->nom;
  1782. $contact_emails['thirdparty']=$langs->trans("ThirdParty").': '.dol_trunc($this->name,16)." &lt;".$this->email."&gt;";
  1783. }
  1784. //var_dump($contact_emails)
  1785. return $contact_emails;
  1786. }
  1787. /**
  1788. * Return list of contacts mobile phone existing for third party
  1789. *
  1790. * @return array Array of contacts emails
  1791. */
  1792. function thirdparty_and_contact_phone_array()
  1793. {
  1794. global $langs;
  1795. $contact_phone = $this->contact_property_array('mobile');
  1796. if (! empty($this->phone)) // If a phone of thirdparty is defined, we add it ot mobile of contacts
  1797. {
  1798. if (empty($this->name)) $this->name=$this->nom;
  1799. // TODO: Tester si tel non deja present dans tableau contact
  1800. $contact_phone['thirdparty']=$langs->trans("ThirdParty").': '.dol_trunc($this->name,16)." &lt;".$this->phone."&gt;";
  1801. }
  1802. return $contact_phone;
  1803. }
  1804. /**
  1805. * Return list of contacts emails or mobile existing for third party
  1806. *
  1807. * @param string $mode 'email' or 'mobile'
  1808. * @param int $hidedisabled 1=Hide contact if disabled
  1809. * @return array Array of contacts emails or mobile array(id=>'Name <email>')
  1810. */
  1811. function contact_property_array($mode='email', $hidedisabled=0)
  1812. {
  1813. global $langs;
  1814. $contact_property = array();
  1815. $sql = "SELECT rowid, email, statut, phone_mobile, lastname, poste, firstname";
  1816. $sql.= " FROM ".MAIN_DB_PREFIX."socpeople";
  1817. $sql.= " WHERE fk_soc = ".$this->id;
  1818. $resql=$this->db->query($sql);
  1819. if ($resql)
  1820. {
  1821. $nump = $this->db->num_rows($resql);
  1822. if ($nump)
  1823. {
  1824. $sepa="("; $sepb=")";
  1825. if ($mode == 'email')
  1826. {
  1827. $sepa="&lt;"; $sepb="&gt;";
  1828. }
  1829. $i = 0;
  1830. while ($i < $nump)
  1831. {
  1832. $obj = $this->db->fetch_object($resql);
  1833. if ($mode == 'email') $property=$obj->email;
  1834. else if ($mode == 'mobile') $property=$obj->phone_mobile;
  1835. else $property=$obj->$mode;
  1836. // Show all contact. If hidedisabled is 1, showonly contacts with status = 1
  1837. if ($obj->statut == 1 || empty($hidedisabled))
  1838. {
  1839. if (empty($property))
  1840. {
  1841. if ($mode == 'email') $property=$langs->trans("NoEMail");
  1842. else if ($mode == 'mobile') $property=$langs->trans("NoMobilePhone");
  1843. }
  1844. if (!empty($obj->poste))
  1845. {
  1846. $contact_property[$obj->rowid] = trim(dolGetFirstLastname($obj->firstname,$obj->lastname)).($obj->poste?" - ".$obj->poste:"").(($mode != 'poste' && $property)?" ".$sepa.$property.$sepb:'');
  1847. }
  1848. else
  1849. {
  1850. $contact_property[$obj->rowid] = trim(dolGetFirstLastname($obj->firstname,$obj->lastname)).(($mode != 'poste' && $property)?" ".$sepa.$property.$sepb:'');
  1851. }
  1852. }
  1853. $i++;
  1854. }
  1855. }
  1856. }
  1857. else
  1858. {
  1859. dol_print_error($this->db);
  1860. }
  1861. return $contact_property;
  1862. }
  1863. /**
  1864. * Renvoie la liste des contacts de cette societe
  1865. *
  1866. * @return array tableau des contacts
  1867. */
  1868. function contact_array()
  1869. {
  1870. $contacts = array();
  1871. $sql = "SELECT rowid, lastname, firstname FROM ".MAIN_DB_PREFIX."socpeople WHERE fk_soc = ".$this->id;
  1872. $resql=$this->db->query($sql);
  1873. if ($resql)
  1874. {
  1875. $nump = $this->db->num_rows($resql);
  1876. if ($nump)
  1877. {
  1878. $i = 0;
  1879. while ($i < $nump)
  1880. {
  1881. $obj = $this->db->fetch_object($resql);
  1882. $contacts[$obj->rowid] = dolGetFirstLastname($obj->firstname,$obj->lastname);
  1883. $i++;
  1884. }
  1885. }
  1886. }
  1887. else
  1888. {
  1889. dol_print_error($this->db);
  1890. }
  1891. return $contacts;
  1892. }
  1893. /**
  1894. * Renvoie la liste des contacts de cette societe
  1895. *
  1896. * @return array $contacts tableau des contacts
  1897. */
  1898. function contact_array_objects()
  1899. {
  1900. require_once DOL_DOCUMENT_ROOT . '/contact/class/contact.class.php';
  1901. $contacts = array();
  1902. $sql = "SELECT rowid FROM ".MAIN_DB_PREFIX."socpeople WHERE fk_soc = ".$this->id;
  1903. $resql=$this->db->query($sql);
  1904. if ($resql)
  1905. {
  1906. $nump = $this->db->num_rows($resql);
  1907. if ($nump)
  1908. {
  1909. $i = 0;
  1910. while ($i < $nump)
  1911. {
  1912. $obj = $this->db->fetch_object($resql);
  1913. $contact = new Contact($this->db);
  1914. $contact->fetch($obj->rowid);
  1915. $contacts[] = $contact;
  1916. $i++;
  1917. }
  1918. }
  1919. }
  1920. else
  1921. {
  1922. dol_print_error($this->db);
  1923. }
  1924. return $contacts;
  1925. }
  1926. /**
  1927. * Return property of contact from its id
  1928. *
  1929. * @param int $rowid id of contact
  1930. * @param string $mode 'email' or 'mobile'
  1931. * @return string Email of contact with format: "Full name <email>"
  1932. */
  1933. function contact_get_property($rowid,$mode)
  1934. {
  1935. $contact_property='';
  1936. if (empty($rowid)) return '';
  1937. $sql = "SELECT rowid, email, phone_mobile, lastname, firstname";
  1938. $sql.= " FROM ".MAIN_DB_PREFIX."socpeople";
  1939. $sql.= " WHERE rowid = '".$rowid."'";
  1940. $resql=$this->db->query($sql);
  1941. if ($resql)
  1942. {
  1943. $nump = $this->db->num_rows($resql);
  1944. if ($nump)
  1945. {
  1946. $obj = $this->db->fetch_object($resql);
  1947. if ($mode == 'email') $contact_property = dolGetFirstLastname($obj->firstname, $obj->lastname)." <".$obj->email.">";
  1948. else if ($mode == 'mobile') $contact_property = $obj->phone_mobile;
  1949. }
  1950. return $contact_property;
  1951. }
  1952. else
  1953. {
  1954. dol_print_error($this->db);
  1955. }
  1956. }
  1957. /**
  1958. * Return bank number property of thirdparty (label or rum)
  1959. *
  1960. * @param string $mode 'label' or 'rum'
  1961. * @return string Bank number
  1962. */
  1963. function display_rib($mode='label')
  1964. {
  1965. require_once DOL_DOCUMENT_ROOT . '/societe/class/companybankaccount.class.php';
  1966. $bac = new CompanyBankAccount($this->db);
  1967. $bac->fetch(0,$this->id);
  1968. if ($mode == 'label')
  1969. {
  1970. return $bac->getRibLabel(true);
  1971. }
  1972. elseif ($mode == 'rum')
  1973. {
  1974. if (empty($bac->rum))
  1975. {
  1976. require_once DOL_DOCUMENT_ROOT . '/compta/prelevement/class/bonprelevement.class.php';
  1977. $prelevement = new BonPrelevement($this->db);
  1978. $bac->fetch_thirdparty();
  1979. $bac->rum = $prelevement->buildRumNumber($bac->thirdparty->code_client, $bac->datec, $bac->id);
  1980. }
  1981. return $bac->rum;
  1982. }
  1983. return 'BadParameterToFunctionDisplayRib';
  1984. }
  1985. /**
  1986. * Return Array of RIB
  1987. *
  1988. * @return array|int 0 if KO, Array of CompanyBanckAccount if OK
  1989. */
  1990. function get_all_rib()
  1991. {
  1992. require_once DOL_DOCUMENT_ROOT . '/societe/class/companybankaccount.class.php';
  1993. $sql = "SELECT rowid FROM ".MAIN_DB_PREFIX."societe_rib WHERE fk_soc = ".$this->id;
  1994. $result = $this->db->query($sql);
  1995. if (!$result) {
  1996. $this->error++;
  1997. $this->errors[] = $this->db->lasterror;
  1998. return 0;
  1999. } else {
  2000. $num_rows = $this->db->num_rows($result);
  2001. $rib_array = array();
  2002. if ($num_rows) {
  2003. while ($obj = $this->db->fetch_object($result)) {
  2004. $rib = new CompanyBankAccount($this->db);
  2005. $rib->fetch($obj->rowid);
  2006. $rib_array[] = $rib;
  2007. }
  2008. }
  2009. return $rib_array;
  2010. }
  2011. }
  2012. /**
  2013. * Attribut un code client a partir du module de controle des codes.
  2014. * Return value is stored into this->code_client
  2015. *
  2016. * @param Societe $objsoc Object thirdparty
  2017. * @param int $type Should be 0 to say customer
  2018. * @return void
  2019. */
  2020. function get_codeclient($objsoc=0,$type=0)
  2021. {
  2022. global $conf;
  2023. if (! empty($conf->global->SOCIETE_CODECLIENT_ADDON))
  2024. {
  2025. $module=$conf->global->SOCIETE_CODECLIENT_ADDON;
  2026. $dirsociete=array_merge(array('/core/modules/societe/'),$conf->modules_parts['societe']);
  2027. foreach ($dirsociete as $dirroot)
  2028. {
  2029. $res=dol_include_once($dirroot.$module.'.php');
  2030. if ($res) break;
  2031. }
  2032. $mod = new $module();
  2033. $this->code_client = $mod->getNextValue($objsoc,$type);
  2034. $this->prefixCustomerIsRequired = $mod->prefixIsRequired;
  2035. dol_syslog(get_class($this)."::get_codeclient code_client=".$this->code_client." module=".$module);
  2036. }
  2037. }
  2038. /**
  2039. * Attribut un code fournisseur a partir du module de controle des codes.
  2040. * Return value is stored into this->code_fournisseur
  2041. *
  2042. * @param Societe $objsoc Object thirdparty
  2043. * @param int $type Should be 1 to say supplier
  2044. * @return void
  2045. */
  2046. function get_codefournisseur($objsoc=0,$type=1)
  2047. {
  2048. global $conf;
  2049. if (! empty($conf->global->SOCIETE_CODECLIENT_ADDON))
  2050. {
  2051. $module=$conf->global->SOCIETE_CODECLIENT_ADDON;
  2052. $dirsociete=array_merge(array('/core/modules/societe/'),$conf->modules_parts['societe']);
  2053. foreach ($dirsociete as $dirroot)
  2054. {
  2055. $res=dol_include_once($dirroot.$module.'.php');
  2056. if ($res) break;
  2057. }
  2058. $mod = new $module();
  2059. $this->code_fournisseur = $mod->getNextValue($objsoc,$type);
  2060. dol_syslog(get_class($this)."::get_codefournisseur code_fournisseur=".$this->code_fournisseur." module=".$module);
  2061. }
  2062. }
  2063. /**
  2064. * Verifie si un code client est modifiable en fonction des parametres
  2065. * du module de controle des codes.
  2066. *
  2067. * @return int 0=No, 1=Yes
  2068. */
  2069. function codeclient_modifiable()
  2070. {
  2071. global $conf;
  2072. if (! empty($conf->global->SOCIETE_CODECLIENT_ADDON))
  2073. {
  2074. $module=$conf->global->SOCIETE_CODECLIENT_ADDON;
  2075. $dirsociete=array_merge(array('/core/modules/societe/'),$conf->modules_parts['societe']);
  2076. foreach ($dirsociete as $dirroot)
  2077. {
  2078. $res=dol_include_once($dirroot.$module.'.php');
  2079. if ($res) break;
  2080. }
  2081. $mod = new $module();
  2082. dol_syslog(get_class($this)."::codeclient_modifiable code_client=".$this->code_client." module=".$module);
  2083. if ($mod->code_modifiable_null && ! $this->code_client) return 1;
  2084. if ($mod->code_modifiable_invalide && $this->check_codeclient() < 0) return 1;
  2085. if ($mod->code_modifiable) return 1; // A mettre en dernier
  2086. return 0;
  2087. }
  2088. else
  2089. {
  2090. return 0;
  2091. }
  2092. }
  2093. /**
  2094. * Verifie si un code fournisseur est modifiable dans configuration du module de controle des codes
  2095. *
  2096. * @return int 0=No, 1=Yes
  2097. */
  2098. function codefournisseur_modifiable()
  2099. {
  2100. global $conf;
  2101. if (! empty($conf->global->SOCIETE_CODECLIENT_ADDON))
  2102. {
  2103. $module=$conf->global->SOCIETE_CODECLIENT_ADDON;
  2104. $dirsociete=array_merge(array('/core/modules/societe/'),$conf->modules_parts['societe']);
  2105. foreach ($dirsociete as $dirroot)
  2106. {
  2107. $res=dol_include_once($dirroot.$module.'.php');
  2108. if ($res) break;
  2109. }
  2110. $mod = new $module();
  2111. dol_syslog(get_class($this)."::codefournisseur_modifiable code_founisseur=".$this->code_fournisseur." module=".$module);
  2112. if ($mod->code_modifiable_null && ! $this->code_fournisseur) return 1;
  2113. if ($mod->code_modifiable_invalide && $this->check_codefournisseur() < 0) return 1;
  2114. if ($mod->code_modifiable) return 1; // A mettre en dernier
  2115. return 0;
  2116. }
  2117. else
  2118. {
  2119. return 0;
  2120. }
  2121. }
  2122. /**
  2123. * Check customer code
  2124. *
  2125. * @return int 0 if OK
  2126. * -1 ErrorBadCustomerCodeSyntax
  2127. * -2 ErrorCustomerCodeRequired
  2128. * -3 ErrorCustomerCodeAlreadyUsed
  2129. * -4 ErrorPrefixRequired
  2130. */
  2131. function check_codeclient()
  2132. {
  2133. global $conf;
  2134. if (! empty($conf->global->SOCIETE_CODECLIENT_ADDON))
  2135. {
  2136. $module=$conf->global->SOCIETE_CODECLIENT_ADDON;
  2137. $dirsociete=array_merge(array('/core/modules/societe/'),$conf->modules_parts['societe']);
  2138. foreach ($dirsociete as $dirroot)
  2139. {
  2140. $res=dol_include_once($dirroot.$module.'.php');
  2141. if ($res) break;
  2142. }
  2143. $mod = new $module();
  2144. dol_syslog(get_class($this)."::check_codeclient code_client=".$this->code_client." module=".$module);
  2145. $result = $mod->verif($this->db, $this->code_client, $this, 0);
  2146. return $result;
  2147. }
  2148. else
  2149. {
  2150. return 0;
  2151. }
  2152. }
  2153. /**
  2154. * Check supplier code
  2155. *
  2156. * @return int 0 if OK
  2157. * -1 ErrorBadCustomerCodeSyntax
  2158. * -2 ErrorCustomerCodeRequired
  2159. * -3 ErrorCustomerCodeAlreadyUsed
  2160. * -4 ErrorPrefixRequired
  2161. */
  2162. function check_codefournisseur()
  2163. {
  2164. global $conf;
  2165. if (! empty($conf->global->SOCIETE_CODECLIENT_ADDON))
  2166. {
  2167. $module=$conf->global->SOCIETE_CODECLIENT_ADDON;
  2168. $dirsociete=array_merge(array('/core/modules/societe/'),$conf->modules_parts['societe']);
  2169. foreach ($dirsociete as $dirroot)
  2170. {
  2171. $res=dol_include_once($dirroot.$module.'.php');
  2172. if ($res) break;
  2173. }
  2174. $mod = new $module();
  2175. dol_syslog(get_class($this)."::check_codefournisseur code_fournisseur=".$this->code_fournisseur." module=".$module);
  2176. $result = $mod->verif($this->db, $this->code_fournisseur, $this, 1);
  2177. return $result;
  2178. }
  2179. else
  2180. {
  2181. return 0;
  2182. }
  2183. }
  2184. /**
  2185. * Renvoie un code compta, suivant le module de code compta.
  2186. * Peut etre identique a celui saisit ou genere automatiquement.
  2187. * A ce jour seule la generation automatique est implementee
  2188. *
  2189. * @param string $type Type of thirdparty ('customer' or 'supplier')
  2190. * @return string Code compta si ok, 0 si aucun, <0 si ko
  2191. */
  2192. function get_codecompta($type)
  2193. {
  2194. global $conf;
  2195. if (! empty($conf->global->SOCIETE_CODECOMPTA_ADDON))
  2196. {
  2197. $file='';
  2198. $dirsociete=array_merge(array('/core/modules/societe/'), $conf->modules_parts['societe']);
  2199. foreach ($dirsociete as $dirroot)
  2200. {
  2201. if (file_exists(DOL_DOCUMENT_ROOT.'/'.$dirroot.$conf->global->SOCIETE_CODECOMPTA_ADDON.".php"))
  2202. {
  2203. $file=$dirroot.$conf->global->SOCIETE_CODECOMPTA_ADDON.".php";
  2204. break;
  2205. }
  2206. }
  2207. if (! empty($file))
  2208. {
  2209. dol_include_once($file);
  2210. $classname = $conf->global->SOCIETE_CODECOMPTA_ADDON;
  2211. $mod = new $classname;
  2212. // Defini code compta dans $mod->code
  2213. $result = $mod->get_code($this->db, $this, $type);
  2214. if ($type == 'customer') $this->code_compta = $mod->code;
  2215. else if ($type == 'supplier') $this->code_compta_fournisseur = $mod->code;
  2216. return $result;
  2217. }
  2218. else
  2219. {
  2220. $this->error = 'ErrorAccountancyCodeNotDefined';
  2221. return -1;
  2222. }
  2223. }
  2224. else
  2225. {
  2226. if ($type == 'customer') $this->code_compta = '';
  2227. else if ($type == 'supplier') $this->code_compta_fournisseur = '';
  2228. return 0;
  2229. }
  2230. }
  2231. /**
  2232. * Define parent commany of current company
  2233. *
  2234. * @param int $id Id of thirdparty to set or '' to remove
  2235. * @return int <0 if KO, >0 if OK
  2236. */
  2237. function set_parent($id)
  2238. {
  2239. if ($this->id)
  2240. {
  2241. $sql = "UPDATE ".MAIN_DB_PREFIX."societe";
  2242. $sql.= " SET parent = ".($id > 0 ? $id : "null");
  2243. $sql.= " WHERE rowid = " . $this->id;
  2244. dol_syslog(get_class($this).'::set_parent', LOG_DEBUG);
  2245. $resql=$this->db->query($sql);
  2246. if ($resql)
  2247. {
  2248. $this->parent = $id;
  2249. return 1;
  2250. }
  2251. else
  2252. {
  2253. return -1;
  2254. }
  2255. }
  2256. else return -1;
  2257. }
  2258. /**
  2259. * Returns if a profid sould be verified
  2260. *
  2261. * @param int $idprof 1,2,3,4 (Exemple: 1=siren,2=siret,3=naf,4=rcs/rm)
  2262. * @return boolean true , false
  2263. */
  2264. function id_prof_verifiable($idprof)
  2265. {
  2266. global $conf;
  2267. switch($idprof)
  2268. {
  2269. case 1:
  2270. $ret=(!$conf->global->SOCIETE_IDPROF1_UNIQUE?false:true);
  2271. break;
  2272. case 2:
  2273. $ret=(!$conf->global->SOCIETE_IDPROF2_UNIQUE?false:true);
  2274. break;
  2275. case 3:
  2276. $ret=(!$conf->global->SOCIETE_IDPROF3_UNIQUE?false:true);
  2277. break;
  2278. case 4:
  2279. $ret=(!$conf->global->SOCIETE_IDPROF4_UNIQUE?false:true);
  2280. break;
  2281. default:
  2282. $ret=false;
  2283. }
  2284. return $ret;
  2285. }
  2286. /**
  2287. * Verify if a profid exists into database for others thirds
  2288. *
  2289. * @param int $idprof 1,2,3,4 (Example: 1=siren,2=siret,3=naf,4=rcs/rm)
  2290. * @param string $value Value of profid
  2291. * @param int $socid Id of thirdparty if update
  2292. * @return boolean true if exists, false if not
  2293. */
  2294. function id_prof_exists($idprof,$value,$socid=0)
  2295. {
  2296. switch($idprof)
  2297. {
  2298. case 1:
  2299. $field="siren";
  2300. break;
  2301. case 2:
  2302. $field="siret";
  2303. break;
  2304. case 3:
  2305. $field="ape";
  2306. break;
  2307. case 4:
  2308. $field="idprof4";
  2309. break;
  2310. }
  2311. //Verify duplicate entries
  2312. $sql = "SELECT COUNT(*) as idprof FROM ".MAIN_DB_PREFIX."societe WHERE ".$field." = '".$value."' AND entity IN (".getEntity('societe',1).")";
  2313. if($socid) $sql .= " AND rowid <> ".$socid;
  2314. $resql = $this->db->query($sql);
  2315. if ($resql)
  2316. {
  2317. $obj = $this->db->fetch_object($resql);
  2318. $count = $obj->idprof;
  2319. }
  2320. else
  2321. {
  2322. $count = 0;
  2323. print $this->db->error();
  2324. }
  2325. $this->db->free($resql);
  2326. if ($count > 0) return true;
  2327. else return false;
  2328. }
  2329. /**
  2330. * Verifie la validite d'un identifiant professionnel en fonction du pays de la societe (siren, siret, ...)
  2331. *
  2332. * @param int $idprof 1,2,3,4 (Exemple: 1=siren,2=siret,3=naf,4=rcs/rm)
  2333. * @param Societe $soc Objet societe
  2334. * @return int <=0 if KO, >0 if OK
  2335. * TODO better to have this in a lib than into a business class
  2336. */
  2337. function id_prof_check($idprof,$soc)
  2338. {
  2339. global $conf;
  2340. $ok=1;
  2341. if (! empty($conf->global->MAIN_DISABLEPROFIDRULES)) return 1;
  2342. // Verifie SIREN si pays FR
  2343. if ($idprof == 1 && $soc->country_code == 'FR')
  2344. {
  2345. $chaine=trim($this->idprof1);
  2346. $chaine=preg_replace('/(\s)/','',$chaine);
  2347. if (dol_strlen($chaine) != 9) return -1;
  2348. $sum = 0;
  2349. for ($i = 0 ; $i < 10 ; $i = $i+2)
  2350. {
  2351. $sum = $sum + substr($this->idprof1, (8 - $i), 1);
  2352. }
  2353. for ($i = 1 ; $i < 9 ; $i = $i+2)
  2354. {
  2355. $ps = 2 * substr($this->idprof1, (8 - $i), 1);
  2356. if ($ps > 9)
  2357. {
  2358. $ps = substr($ps, 0,1) + substr($ps, 1, 1);
  2359. }
  2360. $sum = $sum + $ps;
  2361. }
  2362. if (substr($sum, -1) != 0) return -1;
  2363. }
  2364. // Verifie SIRET si pays FR
  2365. if ($idprof == 2 && $soc->country_code == 'FR')
  2366. {
  2367. $chaine=trim($this->idprof2);
  2368. $chaine=preg_replace('/(\s)/','',$chaine);
  2369. if (dol_strlen($chaine) != 14) return -1;
  2370. }
  2371. //Verify CIF/NIF/NIE if pays ES
  2372. //Returns: 1 if NIF ok, 2 if CIF ok, 3 if NIE ok, -1 if NIF bad, -2 if CIF bad, -3 if NIE bad, 0 if unexpected bad
  2373. if ($idprof == 1 && $soc->country_code == 'ES')
  2374. {
  2375. $string=trim($this->idprof1);
  2376. $string=preg_replace('/(\s)/','',$string);
  2377. $string = strtoupper($string);
  2378. for ($i = 0; $i < 9; $i ++)
  2379. $num[$i] = substr($string, $i, 1);
  2380. //Check format
  2381. if (!preg_match('/((^[A-Z]{1}[0-9]{7}[A-Z0-9]{1}$|^[T]{1}[A-Z0-9]{8}$)|^[0-9]{8}[A-Z]{1}$)/', $string))
  2382. return 0;
  2383. //Check NIF
  2384. if (preg_match('/(^[0-9]{8}[A-Z]{1}$)/', $string))
  2385. if ($num[8] == substr('TRWAGMYFPDXBNJZSQVHLCKE', substr($string, 0, 8) % 23, 1))
  2386. return 1;
  2387. else
  2388. return -1;
  2389. //algorithm checking type code CIF
  2390. $sum = $num[2] + $num[4] + $num[6];
  2391. for ($i = 1; $i < 8; $i += 2)
  2392. $sum += substr((2 * $num[$i]),0,1) + substr((2 * $num[$i]),1,1);
  2393. $n = 10 - substr($sum, strlen($sum) - 1, 1);
  2394. //Chek special NIF
  2395. if (preg_match('/^[KLM]{1}/', $string))
  2396. if ($num[8] == chr(64 + $n) || $num[8] == substr('TRWAGMYFPDXBNJZSQVHLCKE', substr($string, 1, 8) % 23, 1))
  2397. return 1;
  2398. else
  2399. return -1;
  2400. //Check CIF
  2401. if (preg_match('/^[ABCDEFGHJNPQRSUVW]{1}/', $string))
  2402. if ($num[8] == chr(64 + $n) || $num[8] == substr($n, strlen($n) - 1, 1))
  2403. return 2;
  2404. else
  2405. return -2;
  2406. //Check NIE T
  2407. if (preg_match('/^[T]{1}/', $string))
  2408. if ($num[8] == preg_match('/^[T]{1}[A-Z0-9]{8}$/', $string))
  2409. return 3;
  2410. else
  2411. return -3;
  2412. //Check NIE XYZ
  2413. if (preg_match('/^[XYZ]{1}/', $string))
  2414. if ($num[8] == substr('TRWAGMYFPDXBNJZSQVHLCKE', substr(str_replace(array('X','Y','Z'), array('0','1','2'), $string), 0, 8) % 23, 1))
  2415. return 3;
  2416. else
  2417. return -3;
  2418. //Can not be verified
  2419. return -4;
  2420. }
  2421. return $ok;
  2422. }
  2423. /**
  2424. * Return an url to check online a professional id or empty string
  2425. *
  2426. * @param int $idprof 1,2,3,4 (Example: 1=siren,2=siret,3=naf,4=rcs/rm)
  2427. * @param Societe $thirdparty Object thirdparty
  2428. * @return string Url or empty string if no URL known
  2429. * TODO better in a lib than into business class
  2430. */
  2431. function id_prof_url($idprof,$thirdparty)
  2432. {
  2433. global $conf,$langs,$hookmanager;
  2434. $url='';
  2435. $action = '';
  2436. $hookmanager->initHooks(array('idprofurl'));
  2437. $parameters=array('idprof'=>$idprof, 'company'=>$thirdparty);
  2438. $reshook=$hookmanager->executeHooks('getIdProfUrl',$parameters,$this,$action); // Note that $action and $object may have been modified by some hooks
  2439. if (empty($reshook))
  2440. {
  2441. if (! empty($conf->global->MAIN_DISABLEPROFIDRULES)) return '';
  2442. // TODO Move links to validate professional ID into a dictionary table "country" + "link"
  2443. if ($idprof == 1 && $thirdparty->country_code == 'FR') $url='http://www.societe.com/cgi-bin/search?champs='.$thirdparty->idprof1; // See also http://avis-situation-sirene.insee.fr/
  2444. //if ($idprof == 1 && ($thirdparty->country_code == 'GB' || $thirdparty->country_code == 'UK')) $url='http://www.companieshouse.gov.uk/WebCHeck/findinfolink/'; // Link no more valid
  2445. if ($idprof == 1 && $thirdparty->country_code == 'ES') $url='http://www.e-informa.es/servlet/app/portal/ENTP/screen/SProducto/prod/ETIQUETA_EMPRESA/nif/'.$thirdparty->idprof1;
  2446. if ($idprof == 1 && $thirdparty->country_code == 'IN') $url='http://www.tinxsys.com/TinxsysInternetWeb/dealerControllerServlet?tinNumber='.$thirdparty->idprof1.';&searchBy=TIN&backPage=searchByTin_Inter.jsp';
  2447. if ($url) return '<a target="_blank" href="'.$url.'">'.$langs->trans("Check").'</a>';
  2448. }
  2449. else
  2450. {
  2451. return $hookmanager->resPrint;
  2452. }
  2453. return '';
  2454. }
  2455. /**
  2456. * Indique si la societe a des projets
  2457. *
  2458. * @return bool true si la societe a des projets, false sinon
  2459. */
  2460. function has_projects()
  2461. {
  2462. $sql = 'SELECT COUNT(*) as numproj FROM '.MAIN_DB_PREFIX.'projet WHERE fk_soc = ' . $this->id;
  2463. $resql = $this->db->query($sql);
  2464. if ($resql)
  2465. {
  2466. $obj = $this->db->fetch_object($resql);
  2467. $count = $obj->numproj;
  2468. }
  2469. else
  2470. {
  2471. $count = 0;
  2472. print $this->db->error();
  2473. }
  2474. $this->db->free($resql);
  2475. return ($count > 0);
  2476. }
  2477. /**
  2478. * Load information for tab info
  2479. *
  2480. * @param int $id Id of thirdparty to load
  2481. * @return void
  2482. */
  2483. function info($id)
  2484. {
  2485. $sql = "SELECT s.rowid, s.nom as name, s.datec as date_creation, tms as date_modification,";
  2486. $sql.= " fk_user_creat, fk_user_modif";
  2487. $sql.= " FROM ".MAIN_DB_PREFIX."societe as s";
  2488. $sql.= " WHERE s.rowid = ".$id;
  2489. $result=$this->db->query($sql);
  2490. if ($result)
  2491. {
  2492. if ($this->db->num_rows($result))
  2493. {
  2494. $obj = $this->db->fetch_object($result);
  2495. $this->id = $obj->rowid;
  2496. if ($obj->fk_user_creat) {
  2497. $cuser = new User($this->db);
  2498. $cuser->fetch($obj->fk_user_creat);
  2499. $this->user_creation = $cuser;
  2500. }
  2501. if ($obj->fk_user_modif) {
  2502. $muser = new User($this->db);
  2503. $muser->fetch($obj->fk_user_modif);
  2504. $this->user_modification = $muser;
  2505. }
  2506. $this->ref = $obj->name;
  2507. $this->date_creation = $this->db->jdate($obj->date_creation);
  2508. $this->date_modification = $this->db->jdate($obj->date_modification);
  2509. }
  2510. $this->db->free($result);
  2511. }
  2512. else
  2513. {
  2514. dol_print_error($this->db);
  2515. }
  2516. }
  2517. /**
  2518. * Return if third party is a company (Business) or an end user (Consumer)
  2519. *
  2520. * @return boolean true=is a company, false=a and user
  2521. */
  2522. function isACompany()
  2523. {
  2524. global $conf;
  2525. // Define if third party is treated as company (or not) when nature is unknown
  2526. $isacompany=empty($conf->global->MAIN_UNKNOWN_CUSTOMERS_ARE_COMPANIES)?0:1; // 0 by default
  2527. if (! empty($this->tva_intra)) $isacompany=1;
  2528. else if (! empty($this->typent_code) && in_array($this->typent_code,array('TE_PRIVATE'))) $isacompany=0;
  2529. else if (! empty($this->typent_code) && in_array($this->typent_code,array('TE_SMALL','TE_MEDIUM','TE_LARGE'))) $isacompany=1;
  2530. return $isacompany;
  2531. }
  2532. /**
  2533. * Charge la liste des categories fournisseurs
  2534. *
  2535. * @return int 0 if success, <> 0 if error
  2536. */
  2537. function LoadSupplierCateg()
  2538. {
  2539. $this->SupplierCategories = array();
  2540. $sql = "SELECT rowid, label";
  2541. $sql.= " FROM ".MAIN_DB_PREFIX."categorie";
  2542. $sql.= " WHERE type = ".Categorie::TYPE_SUPPLIER;
  2543. $resql=$this->db->query($sql);
  2544. if ($resql)
  2545. {
  2546. while ($obj = $this->db->fetch_object($resql) )
  2547. {
  2548. $this->SupplierCategories[$obj->rowid] = $obj->label;
  2549. }
  2550. return 0;
  2551. }
  2552. else
  2553. {
  2554. return -1;
  2555. }
  2556. }
  2557. /**
  2558. * Charge la liste des categories fournisseurs
  2559. *
  2560. * @param int $categorie_id Id of category
  2561. * @return int 0 if success, <> 0 if error
  2562. */
  2563. function AddFournisseurInCategory($categorie_id)
  2564. {
  2565. if ($categorie_id > 0)
  2566. {
  2567. $sql = "INSERT INTO ".MAIN_DB_PREFIX."categorie_fournisseur (fk_categorie, fk_soc) ";
  2568. $sql.= " VALUES ('".$categorie_id."','".$this->id."');";
  2569. if ($resql=$this->db->query($sql)) return 0;
  2570. }
  2571. else
  2572. {
  2573. return 0;
  2574. }
  2575. return -1;
  2576. }
  2577. /**
  2578. * Create a third party into database from a member object
  2579. *
  2580. * @param Adherent $member Object member
  2581. * @param string $socname Name of third party to force
  2582. * @return int <0 if KO, id of created account if OK
  2583. */
  2584. function create_from_member(Adherent $member,$socname='')
  2585. {
  2586. global $user,$langs;
  2587. $name = $socname?$socname:$member->societe;
  2588. if (empty($name)) $name=$member->getFullName($langs);
  2589. // Positionne parametres
  2590. $this->nom=$name; // TODO deprecated
  2591. $this->name=$name;
  2592. $this->address=$member->address;
  2593. $this->zip=$member->zip;
  2594. $this->town=$member->town;
  2595. $this->country_code=$member->country_code;
  2596. $this->country_id=$member->country_id;
  2597. $this->phone=$member->phone; // Prof phone
  2598. $this->email=$member->email;
  2599. $this->skype=$member->skype;
  2600. $this->client = 1; // A member is a customer by default
  2601. $this->code_client = -1;
  2602. $this->code_fournisseur = -1;
  2603. $this->db->begin();
  2604. // Cree et positionne $this->id
  2605. $result=$this->create($user);
  2606. if ($result >= 0)
  2607. {
  2608. $sql = "UPDATE ".MAIN_DB_PREFIX."adherent";
  2609. $sql.= " SET fk_soc=".$this->id;
  2610. $sql.= " WHERE rowid=".$member->id;
  2611. dol_syslog(get_class($this)."::create_from_member", LOG_DEBUG);
  2612. $resql=$this->db->query($sql);
  2613. if ($resql)
  2614. {
  2615. $this->db->commit();
  2616. return $this->id;
  2617. }
  2618. else
  2619. {
  2620. $this->error=$this->db->error();
  2621. $this->db->rollback();
  2622. return -1;
  2623. }
  2624. }
  2625. else
  2626. {
  2627. // $this->error deja positionne
  2628. dol_syslog(get_class($this)."::create_from_member - 2 - ".$this->error." - ".join(',',$this->errors), LOG_ERR);
  2629. $this->db->rollback();
  2630. return $result;
  2631. }
  2632. }
  2633. /**
  2634. * Set properties with value into $conf
  2635. *
  2636. * @param Conf $conf Conf object (possibility to use another entity)
  2637. * @return void
  2638. */
  2639. function setMysoc(Conf $conf)
  2640. {
  2641. global $langs;
  2642. $this->id=0;
  2643. $this->name=empty($conf->global->MAIN_INFO_SOCIETE_NOM)?'':$conf->global->MAIN_INFO_SOCIETE_NOM;
  2644. $this->address=empty($conf->global->MAIN_INFO_SOCIETE_ADDRESS)?'':$conf->global->MAIN_INFO_SOCIETE_ADDRESS;
  2645. $this->zip=empty($conf->global->MAIN_INFO_SOCIETE_ZIP)?'':$conf->global->MAIN_INFO_SOCIETE_ZIP;
  2646. $this->town=empty($conf->global->MAIN_INFO_SOCIETE_TOWN)?'':$conf->global->MAIN_INFO_SOCIETE_TOWN;
  2647. $this->state_id=empty($conf->global->MAIN_INFO_SOCIETE_STATE)?'':$conf->global->MAIN_INFO_SOCIETE_STATE;
  2648. /* Disabled: we don't want any SQL request into method setMySoc. This method set object from env only.
  2649. If we need label, label must be loaded by output that need it from id (label depends on output language)
  2650. require_once DOL_DOCUMENT_ROOT .'/core/lib/company.lib.php';
  2651. if (!empty($conf->global->MAIN_INFO_SOCIETE_STATE)) {
  2652. $this->state_id= $conf->global->MAIN_INFO_SOCIETE_STATE;
  2653. $this->state = getState($this->state_id);
  2654. }
  2655. */
  2656. $this->note_private=empty($conf->global->MAIN_INFO_SOCIETE_NOTE)?'':$conf->global->MAIN_INFO_SOCIETE_NOTE;
  2657. $this->nom=$this->name; // deprecated
  2658. // We define country_id, country_code and country
  2659. $country_id=$country_code=$country_label='';
  2660. if (! empty($conf->global->MAIN_INFO_SOCIETE_COUNTRY))
  2661. {
  2662. $tmp=explode(':',$conf->global->MAIN_INFO_SOCIETE_COUNTRY);
  2663. $country_id=$tmp[0];
  2664. if (! empty($tmp[1])) // If $conf->global->MAIN_INFO_SOCIETE_COUNTRY is "id:code:label"
  2665. {
  2666. $country_code=$tmp[1];
  2667. $country_label=$tmp[2];
  2668. }
  2669. else // For backward compatibility
  2670. {
  2671. dol_syslog("Your country setup use an old syntax. Reedit it using setup area.", LOG_ERR);
  2672. include_once DOL_DOCUMENT_ROOT.'/core/lib/company.lib.php';
  2673. $country_code=getCountry($country_id,2,$this->db); // This need a SQL request, but it's the old feature that should not be used anymore
  2674. $country_label=getCountry($country_id,0,$this->db); // This need a SQL request, but it's the old feature that should not be used anymore
  2675. }
  2676. }
  2677. $this->country_id=$country_id;
  2678. $this->country_code=$country_code;
  2679. $this->country=$country_label;
  2680. if (is_object($langs)) $this->country=($langs->trans('Country'.$country_code)!='Country'.$country_code)?$langs->trans('Country'.$country_code):$country_label;
  2681. $this->phone=empty($conf->global->MAIN_INFO_SOCIETE_TEL)?'':$conf->global->MAIN_INFO_SOCIETE_TEL;
  2682. $this->fax=empty($conf->global->MAIN_INFO_SOCIETE_FAX)?'':$conf->global->MAIN_INFO_SOCIETE_FAX;
  2683. $this->url=empty($conf->global->MAIN_INFO_SOCIETE_WEB)?'':$conf->global->MAIN_INFO_SOCIETE_WEB;
  2684. // Id prof generiques
  2685. $this->idprof1=empty($conf->global->MAIN_INFO_SIREN)?'':$conf->global->MAIN_INFO_SIREN;
  2686. $this->idprof2=empty($conf->global->MAIN_INFO_SIRET)?'':$conf->global->MAIN_INFO_SIRET;
  2687. $this->idprof3=empty($conf->global->MAIN_INFO_APE)?'':$conf->global->MAIN_INFO_APE;
  2688. $this->idprof4=empty($conf->global->MAIN_INFO_RCS)?'':$conf->global->MAIN_INFO_RCS;
  2689. $this->idprof5=empty($conf->global->MAIN_INFO_PROFID5)?'':$conf->global->MAIN_INFO_PROFID5;
  2690. $this->idprof6=empty($conf->global->MAIN_INFO_PROFID6)?'':$conf->global->MAIN_INFO_PROFID6;
  2691. $this->tva_intra=empty($conf->global->MAIN_INFO_TVAINTRA)?'':$conf->global->MAIN_INFO_TVAINTRA; // VAT number, not necessarly INTRA.
  2692. $this->managers=empty($conf->global->MAIN_INFO_SOCIETE_MANAGERS)?'':$conf->global->MAIN_INFO_SOCIETE_MANAGERS;
  2693. $this->capital=empty($conf->global->MAIN_INFO_CAPITAL)?'':$conf->global->MAIN_INFO_CAPITAL;
  2694. $this->forme_juridique_code=empty($conf->global->MAIN_INFO_SOCIETE_FORME_JURIDIQUE)?'':$conf->global->MAIN_INFO_SOCIETE_FORME_JURIDIQUE;
  2695. $this->email=empty($conf->global->MAIN_INFO_SOCIETE_MAIL)?'':$conf->global->MAIN_INFO_SOCIETE_MAIL;
  2696. $this->logo=empty($conf->global->MAIN_INFO_SOCIETE_LOGO)?'':$conf->global->MAIN_INFO_SOCIETE_LOGO;
  2697. $this->logo_small=empty($conf->global->MAIN_INFO_SOCIETE_LOGO_SMALL)?'':$conf->global->MAIN_INFO_SOCIETE_LOGO_SMALL;
  2698. $this->logo_mini=empty($conf->global->MAIN_INFO_SOCIETE_LOGO_MINI)?'':$conf->global->MAIN_INFO_SOCIETE_LOGO_MINI;
  2699. // Define if company use vat or not
  2700. $this->tva_assuj=$conf->global->FACTURE_TVAOPTION;
  2701. // Define if company use local taxes
  2702. $this->localtax1_assuj=((isset($conf->global->FACTURE_LOCAL_TAX1_OPTION) && ($conf->global->FACTURE_LOCAL_TAX1_OPTION=='1' || $conf->global->FACTURE_LOCAL_TAX1_OPTION=='localtax1on'))?1:0);
  2703. $this->localtax2_assuj=((isset($conf->global->FACTURE_LOCAL_TAX2_OPTION) && ($conf->global->FACTURE_LOCAL_TAX2_OPTION=='1' || $conf->global->FACTURE_LOCAL_TAX2_OPTION=='localtax2on'))?1:0);
  2704. }
  2705. /**
  2706. * Initialise an instance with random values.
  2707. * Used to build previews or test instances.
  2708. * id must be 0 if object instance is a specimen.
  2709. *
  2710. * @return void
  2711. */
  2712. function initAsSpecimen()
  2713. {
  2714. $now=dol_now();
  2715. // Initialize parameters
  2716. $this->id=0;
  2717. $this->name = 'THIRDPARTY SPECIMEN '.dol_print_date($now,'dayhourlog');
  2718. $this->nom = $this->name; // For backward compatibility
  2719. $this->ref_ext = 'Ref ext';
  2720. $this->specimen=1;
  2721. $this->address='21 jump street';
  2722. $this->zip='99999';
  2723. $this->town='MyTown';
  2724. $this->state_id=1;
  2725. $this->state_code='AA';
  2726. $this->state='MyState';
  2727. $this->country_id=1;
  2728. $this->country_code='FR';
  2729. $this->email='specimen@specimen.com';
  2730. $this->skype='tom.hanson';
  2731. $this->url='http://www.specimen.com';
  2732. $this->phone='0909090901';
  2733. $this->fax='0909090909';
  2734. $this->code_client='CC-'.dol_print_date($now,'dayhourlog');
  2735. $this->code_fournisseur='SC-'.dol_print_date($now,'dayhourlog');
  2736. $this->capital=10000;
  2737. $this->client=1;
  2738. $this->prospect=1;
  2739. $this->fournisseur=1;
  2740. $this->tva_assuj=1;
  2741. $this->tva_intra='EU1234567';
  2742. $this->note_public='This is a comment (public)';
  2743. $this->note_private='This is a comment (private)';
  2744. $this->idprof1='idprof1';
  2745. $this->idprof2='idprof2';
  2746. $this->idprof3='idprof3';
  2747. $this->idprof4='idprof4';
  2748. $this->idprof5='idprof5';
  2749. $this->idprof6='idprof6';
  2750. }
  2751. /**
  2752. * Check if we must use localtax feature or not according to country (country of $mysoc in most cases).
  2753. *
  2754. * @param int $localTaxNum To get info for only localtax1 or localtax2
  2755. * @return boolean true or false
  2756. */
  2757. function useLocalTax($localTaxNum=0)
  2758. {
  2759. $sql = "SELECT t.localtax1, t.localtax2";
  2760. $sql .= " FROM ".MAIN_DB_PREFIX."c_tva as t, ".MAIN_DB_PREFIX."c_country as c";
  2761. $sql .= " WHERE t.fk_pays = c.rowid AND c.code = '".$this->db->escape($this->country_code)."'";
  2762. $sql .= " AND t.active = 1";
  2763. if (empty($localTaxNum)) $sql .= " AND (t.localtax1_type <> '0' OR t.localtax2_type <> '0')";
  2764. elseif ($localTaxNum == 1) $sql .= " AND t.localtax1_type <> '0'";
  2765. elseif ($localTaxNum == 2) $sql .= " AND t.localtax2_type <> '0'";
  2766. dol_syslog("useLocalTax", LOG_DEBUG);
  2767. $resql=$this->db->query($sql);
  2768. if ($resql)
  2769. {
  2770. return ($this->db->num_rows($resql) > 0);
  2771. }
  2772. else return false;
  2773. }
  2774. /**
  2775. * Check if we must use NPR Vat (french stupid rule) or not according to country (country of $mysoc in most cases).
  2776. *
  2777. * @return boolean true or false
  2778. */
  2779. function useNPR()
  2780. {
  2781. $sql = "SELECT t.rowid";
  2782. $sql .= " FROM ".MAIN_DB_PREFIX."c_tva as t, ".MAIN_DB_PREFIX."c_country as c";
  2783. $sql .= " WHERE t.fk_pays = c.rowid AND c.code = '".$this->db->escape($this->country_code)."'";
  2784. $sql .= " AND t.active = 1 AND t.recuperableonly = 1";
  2785. dol_syslog("useNPR", LOG_DEBUG);
  2786. $resql=$this->db->query($sql);
  2787. if ($resql)
  2788. {
  2789. return ($this->db->num_rows($resql) > 0);
  2790. }
  2791. else return false;
  2792. }
  2793. /**
  2794. * Check if we must use revenue stamps feature or not according to country (country of $mysocin most cases).
  2795. *
  2796. * @return boolean true or false
  2797. */
  2798. function useRevenueStamp()
  2799. {
  2800. $sql = "SELECT COUNT(*) as nb";
  2801. $sql .= " FROM ".MAIN_DB_PREFIX."c_revenuestamp as r, ".MAIN_DB_PREFIX."c_country as c";
  2802. $sql .= " WHERE r.fk_pays = c.rowid AND c.code = '".$this->db->escape($this->country_code)."'";
  2803. $sql .= " AND r.active = 1";
  2804. dol_syslog("useRevenueStamp", LOG_DEBUG);
  2805. $resql=$this->db->query($sql);
  2806. if ($resql)
  2807. {
  2808. $obj=$this->db->fetch_object($resql);
  2809. return (($obj->nb > 0)?true:false);
  2810. }
  2811. else
  2812. {
  2813. $this->error=$this->db->lasterror();
  2814. return false;
  2815. }
  2816. }
  2817. /**
  2818. * Return prostect level
  2819. *
  2820. * @return string Libelle
  2821. */
  2822. function getLibProspLevel()
  2823. {
  2824. return $this->LibProspLevel($this->fk_prospectlevel);
  2825. }
  2826. /**
  2827. * Return label of prospect level
  2828. *
  2829. * @param int $fk_prospectlevel Prospect level
  2830. * @return string label of level
  2831. */
  2832. function LibProspLevel($fk_prospectlevel)
  2833. {
  2834. global $langs;
  2835. $lib=$langs->trans("ProspectLevel".$fk_prospectlevel);
  2836. // If lib not found in language file, we get label from cache/databse
  2837. if ($lib == $langs->trans("ProspectLevel".$fk_prospectlevel))
  2838. {
  2839. $lib=$langs->getLabelFromKey($this->db,$fk_prospectlevel,'c_prospectlevel','code','label');
  2840. }
  2841. return $lib;
  2842. }
  2843. /**
  2844. * Set prospect level
  2845. *
  2846. * @param User $user Utilisateur qui definie la remise
  2847. * @return int <0 if KO, >0 if OK
  2848. * @deprecated Use update function instead
  2849. */
  2850. function set_prospect_level(User $user)
  2851. {
  2852. return $this->update($this->id, $user);
  2853. }
  2854. /**
  2855. * Return status of prospect
  2856. *
  2857. * @param int $mode 0=libelle long, 1=libelle court, 2=Picto + Libelle court, 3=Picto, 4=Picto + Libelle long
  2858. * @param string $label Label to use for status for added status
  2859. * @return string Libelle
  2860. */
  2861. function getLibProspCommStatut($mode=0, $label='')
  2862. {
  2863. return $this->LibProspCommStatut($this->stcomm_id, $mode, $label);
  2864. }
  2865. /**
  2866. * Return label of a given status
  2867. *
  2868. * @param int|string $statut Id or code for prospection status
  2869. * @param int $mode 0=long label, 1=short label, 2=Picto + short label, 3=Picto, 4=Picto + long label, 5=Short label + Picto
  2870. * @param string $label Label to use for status for added status
  2871. * @return string Libelle du statut
  2872. */
  2873. function LibProspCommStatut($statut, $mode=0, $label='')
  2874. {
  2875. global $langs;
  2876. $langs->load('customers');
  2877. if ($mode == 2)
  2878. {
  2879. if ($statut == '-1' || $statut == 'ST_NO') return img_action($langs->trans("StatusProspect-1"),-1).' '.$langs->trans("StatusProspect-1");
  2880. elseif ($statut == '0' || $statut == 'ST_NEVER') return img_action($langs->trans("StatusProspect0"), 0).' '.$langs->trans("StatusProspect0");
  2881. elseif ($statut == '1' || $statut == 'ST_TODO') return img_action($langs->trans("StatusProspect1"), 1).' '.$langs->trans("StatusProspect1");
  2882. elseif ($statut == '2' || $statut == 'ST_PEND') return img_action($langs->trans("StatusProspect2"), 2).' '.$langs->trans("StatusProspect2");
  2883. elseif ($statut == '3' || $statut == 'ST_DONE') return img_action($langs->trans("StatusProspect3"), 3).' '.$langs->trans("StatusProspect3");
  2884. else
  2885. {
  2886. return img_action(($langs->trans("StatusProspect".$statut) != "StatusProspect".$statut) ? $langs->trans("StatusProspect".$statut) : $label, 0).' '.(($langs->trans("StatusProspect".$statut) != "StatusProspect".$statut) ? $langs->trans("StatusProspect".$statut) : $label);
  2887. }
  2888. }
  2889. if ($mode == 3)
  2890. {
  2891. if ($statut == '-1' || $statut == 'ST_NO') return img_action($langs->trans("StatusProspect-1"),-1);
  2892. elseif ($statut == '0' || $statut == 'ST_NEVER') return img_action($langs->trans("StatusProspect0"), 0);
  2893. elseif ($statut == '1' || $statut == 'ST_TODO') return img_action($langs->trans("StatusProspect1"), 1);
  2894. elseif ($statut == '2' || $statut == 'ST_PEND') return img_action($langs->trans("StatusProspect2"), 2);
  2895. elseif ($statut == '3' || $statut == 'ST_DONE') return img_action($langs->trans("StatusProspect3"), 3);
  2896. else
  2897. {
  2898. return img_action(($langs->trans("StatusProspect".$statut) != "StatusProspect".$statut) ? $langs->trans("StatusProspect".$statut) : $label, 0);
  2899. }
  2900. }
  2901. if ($mode == 4)
  2902. {
  2903. if ($statut == '-1' || $statut == 'ST_NO') return img_action($langs->trans("StatusProspect-1"),-1).' '.$langs->trans("StatusProspect-1");
  2904. elseif ($statut == '0' || $statut == 'ST_NEVER') return img_action($langs->trans("StatusProspect0"), 0).' '.$langs->trans("StatusProspect0");
  2905. elseif ($statut == '1' || $statut == 'ST_TODO') return img_action($langs->trans("StatusProspect1"), 1).' '.$langs->trans("StatusProspect1");
  2906. elseif ($statut == '2' || $statut == 'ST_PEND') return img_action($langs->trans("StatusProspect2"), 2).' '.$langs->trans("StatusProspect2");
  2907. elseif ($statut == '3' || $statut == 'ST_DONE') return img_action($langs->trans("StatusProspect3"), 3).' '.$langs->trans("StatusProspect3");
  2908. else
  2909. {
  2910. return img_action(($langs->trans("StatusProspect".$statut) != "StatusProspect".$statut) ? $langs->trans("StatusProspect".$statut) : $label, 0).' '.(($langs->trans("StatusProspect".$statut) != "StatusProspect".$statut) ? $langs->trans("StatusProspect".$statut) : $label);
  2911. }
  2912. }
  2913. return "Error, mode/status not found";
  2914. }
  2915. /**
  2916. * Set outstanding value
  2917. *
  2918. * @param User $user User making change
  2919. * @return int <0 if KO, >0 if OK
  2920. * @deprecated Use update function instead
  2921. */
  2922. function set_OutstandingBill(User $user)
  2923. {
  2924. return $this->update($this->id, $user);
  2925. }
  2926. /**
  2927. * Return amount of order not paid and total
  2928. *
  2929. * @param string $mode 'customer' or 'supplier'
  2930. * @return array array('opened'=>Amount, 'total'=>Total amount)
  2931. */
  2932. function getOutstandingProposals($mode='customer')
  2933. {
  2934. $table='propal';
  2935. if ($mode == 'supplier') $table = 'supplier_proposal';
  2936. $sql = "SELECT rowid, total_ht, total as total_ttc, fk_statut FROM ".MAIN_DB_PREFIX.$table." as f";
  2937. $sql .= " WHERE fk_soc = ". $this->id;
  2938. dol_syslog("getOutstandingProposals", LOG_DEBUG);
  2939. $resql=$this->db->query($sql);
  2940. if ($resql)
  2941. {
  2942. $outstandingOpened = 0;
  2943. $outstandingTotal = 0;
  2944. $outstandingTotalIncTax = 0;
  2945. while($obj=$this->db->fetch_object($resql)) {
  2946. $outstandingTotal+= $obj->total_ht;
  2947. $outstandingTotalIncTax+= $obj->total_ttc;
  2948. if ($obj->fk_statut != 0) // Not a draft
  2949. {
  2950. $outstandingOpened+=$obj->total_ttc;
  2951. }
  2952. }
  2953. return array('opened'=>$outstandingOpened, 'total_ht'=>$outstandingTotal, 'total_ttc'=>$outstandingTotalIncTax);
  2954. }
  2955. else
  2956. return array();
  2957. }
  2958. /**
  2959. * Return amount of order not paid and total
  2960. *
  2961. * @param string $mode 'customer' or 'supplier'
  2962. * @return array array('opened'=>Amount, 'total'=>Total amount)
  2963. */
  2964. function getOutstandingOrders($mode='customer')
  2965. {
  2966. $table='commande';
  2967. if ($mode == 'supplier') $table = 'commande_fournisseur';
  2968. $sql = "SELECT rowid, total_ht, total_ttc, fk_statut FROM ".MAIN_DB_PREFIX.$table." as f";
  2969. $sql .= " WHERE fk_soc = ". $this->id;
  2970. dol_syslog("getOutstandingOrders", LOG_DEBUG);
  2971. $resql=$this->db->query($sql);
  2972. if ($resql)
  2973. {
  2974. $outstandingOpened = 0;
  2975. $outstandingTotal = 0;
  2976. $outstandingTotalIncTax = 0;
  2977. while($obj=$this->db->fetch_object($resql)) {
  2978. $outstandingTotal+= $obj->total_ht;
  2979. $outstandingTotalIncTax+= $obj->total_ttc;
  2980. if ($obj->fk_statut != 0) // Not a draft
  2981. {
  2982. $outstandingOpened+=$obj->total_ttc;
  2983. }
  2984. }
  2985. return array('opened'=>$outstandingOpened, 'total_ht'=>$outstandingTotal, 'total_ttc'=>$outstandingTotalIncTax);
  2986. }
  2987. else
  2988. return array();
  2989. }
  2990. /**
  2991. * Return amount of bill not paid and total
  2992. *
  2993. * @param string $mode 'customer' or 'supplier'
  2994. * @return array array('opened'=>Amount, 'total'=>Total amount)
  2995. */
  2996. function getOutstandingBills($mode='customer')
  2997. {
  2998. $table='facture';
  2999. if ($mode == 'supplier') $table = 'facture_fourn';
  3000. /* Accurate value of remain to pay is to sum remaintopay for each invoice
  3001. $paiement = $invoice->getSommePaiement();
  3002. $creditnotes=$invoice->getSumCreditNotesUsed();
  3003. $deposits=$invoice->getSumDepositsUsed();
  3004. $alreadypayed=price2num($paiement + $creditnotes + $deposits,'MT');
  3005. $remaintopay=price2num($invoice->total_ttc - $paiement - $creditnotes - $deposits,'MT');
  3006. */
  3007. if ($mode == 'supplier') $sql = "SELECT rowid, total_ht as total_ht, total_ttc, paye, fk_statut, close_code FROM ".MAIN_DB_PREFIX.$table." as f";
  3008. else $sql = "SELECT rowid, total as total_ht, total_ttc, paye, fk_statut, close_code FROM ".MAIN_DB_PREFIX.$table." as f";
  3009. $sql .= " WHERE fk_soc = ". $this->id;
  3010. dol_syslog("getOutstandingBills", LOG_DEBUG);
  3011. $resql=$this->db->query($sql);
  3012. if ($resql)
  3013. {
  3014. $outstandingOpened = 0;
  3015. $outstandingTotal = 0;
  3016. $outstandingTotalIncTax = 0;
  3017. if ($mode == 'supplier')
  3018. {
  3019. require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.facture.class.php';
  3020. $tmpobject=new FactureFournisseur($this->db);
  3021. }
  3022. else
  3023. {
  3024. require_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture.class.php';
  3025. $tmpobject=new Facture($this->db);
  3026. }
  3027. while($obj=$this->db->fetch_object($resql)) {
  3028. $tmpobject->id=$obj->rowid;
  3029. if ($obj->fk_statut != 0 // Not a draft
  3030. && ! ($obj->fk_statut == 3 && $obj->close_code == 'replaced') // Not a replaced invoice
  3031. )
  3032. {
  3033. $outstandingTotal+= $obj->total_ht;
  3034. $outstandingTotalIncTax+= $obj->total_ttc;
  3035. }
  3036. if ($obj->paye == 0
  3037. && $obj->fk_statut != 0 // Not a draft
  3038. && $obj->fk_statut != 3 // Not abandonned
  3039. && $obj->fk_statut != 2) // Not classified as paid
  3040. //$sql .= " AND (fk_statut <> 3 OR close_code <> 'abandon')"; // Not abandonned for undefined reason
  3041. {
  3042. $paiement = $tmpobject->getSommePaiement();
  3043. $creditnotes = $tmpobject->getSumCreditNotesUsed();
  3044. $deposits = $tmpobject->getSumDepositsUsed();
  3045. $outstandingOpened+=$obj->total_ttc - $paiement - $creditnotes - $deposits;
  3046. }
  3047. }
  3048. return array('opened'=>$outstandingOpened, 'total_ht'=>$outstandingTotal, 'total_ttc'=>$outstandingTotalIncTax);
  3049. }
  3050. else
  3051. {
  3052. return array();
  3053. }
  3054. }
  3055. /**
  3056. * Return amount of bill not paid
  3057. *
  3058. * @return int Amount in debt for thirdparty
  3059. * @deprecated
  3060. */
  3061. function get_OutstandingBill()
  3062. {
  3063. /* Accurate value of remain to pay is to sum remaintopay for each invoice
  3064. $paiement = $invoice->getSommePaiement();
  3065. $creditnotes=$invoice->getSumCreditNotesUsed();
  3066. $deposits=$invoice->getSumDepositsUsed();
  3067. $alreadypayed=price2num($paiement + $creditnotes + $deposits,'MT');
  3068. $remaintopay=price2num($invoice->total_ttc - $paiement - $creditnotes - $deposits,'MT');
  3069. */
  3070. $sql = "SELECT rowid, total_ttc FROM ".MAIN_DB_PREFIX."facture as f";
  3071. $sql .= " WHERE fk_soc = ". $this->id;
  3072. $sql .= " AND paye = 0";
  3073. $sql .= " AND fk_statut <> 0"; // Not a draft
  3074. //$sql .= " AND (fk_statut <> 3 OR close_code <> 'abandon')"; // Not abandonned for undefined reason
  3075. $sql .= " AND fk_statut <> 3"; // Not abandonned
  3076. $sql .= " AND fk_statut <> 2"; // Not clasified as paid
  3077. dol_syslog("get_OutstandingBill", LOG_DEBUG);
  3078. $resql=$this->db->query($sql);
  3079. if ($resql)
  3080. {
  3081. $outstandingAmount = 0;
  3082. require_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture.class.php';
  3083. $tmpobject=new Facture($this->db);
  3084. while($obj=$this->db->fetch_object($resql)) {
  3085. $tmpobject->id=$obj->rowid;
  3086. $paiement = $tmpobject->getSommePaiement();
  3087. $creditnotes = $tmpobject->getSumCreditNotesUsed();
  3088. $deposits = $tmpobject->getSumDepositsUsed();
  3089. $outstandingAmount+= $obj->total_ttc - $paiement - $creditnotes - $deposits;
  3090. }
  3091. return $outstandingAmount;
  3092. }
  3093. else
  3094. return 0;
  3095. }
  3096. /**
  3097. * Return label of status customer is prospect/customer
  3098. *
  3099. * @return string Label
  3100. */
  3101. function getLibCustProspStatut()
  3102. {
  3103. return $this->LibCustProspStatut($this->client);
  3104. }
  3105. /**
  3106. * Renvoi le libelle d'un statut donne
  3107. *
  3108. * @param int $statut Id statut
  3109. * @return string Libelle du statut
  3110. */
  3111. function LibCustProspStatut($statut)
  3112. {
  3113. global $langs;
  3114. $langs->load('companies');
  3115. if ($statut==0) return $langs->trans("NorProspectNorCustomer");
  3116. if ($statut==1) return $langs->trans("Customer");
  3117. if ($statut==2) return $langs->trans("Prospect");
  3118. if ($statut==3) return $langs->trans("ProspectCustomer");
  3119. }
  3120. /**
  3121. * Create a document onto disk according to template module.
  3122. *
  3123. * @param string $modele Generator to use. Caller must set it to obj->modelpdf or GETPOST('modelpdf') for example.
  3124. * @param Translate $outputlangs objet lang a utiliser pour traduction
  3125. * @param int $hidedetails Hide details of lines
  3126. * @param int $hidedesc Hide description
  3127. * @param int $hideref Hide ref
  3128. * @param null|array $moreparams Array to provide more information
  3129. * @return int <0 if KO, >0 if OK
  3130. */
  3131. public function generateDocument($modele, $outputlangs, $hidedetails=0, $hidedesc=0, $hideref=0, $moreparams=null)
  3132. {
  3133. global $conf,$user,$langs;
  3134. if (! empty($moreparams) && ! empty($moreparams['use_companybankid']))
  3135. {
  3136. $modelpath = "core/modules/bank/doc/";
  3137. include_once DOL_DOCUMENT_ROOT.'/societe/class/companybankaccount.class.php';
  3138. $companybankaccount = new CompanyBankAccount($this->db);
  3139. $result = $companybankaccount->fetch($moreparams['use_companybankid']);
  3140. if (! $result) dol_print_error($this->db, $companybankaccount->error, $companybankaccount->errors);
  3141. $result=$companybankaccount->commonGenerateDocument($modelpath, $modele, $outputlangs, $hidedetails, $hidedesc, $hideref, $moreparams);
  3142. }
  3143. else
  3144. {
  3145. // Positionne le modele sur le nom du modele a utiliser
  3146. if (! dol_strlen($modele))
  3147. {
  3148. if (! empty($conf->global->COMPANY_ADDON_PDF))
  3149. {
  3150. $modele = $conf->global->COMPANY_ADDON_PDF;
  3151. }
  3152. else
  3153. {
  3154. print $langs->trans("Error")." ".$langs->trans("Error_COMPANY_ADDON_PDF_NotDefined");
  3155. return 0;
  3156. }
  3157. }
  3158. $modelpath = "core/modules/societe/doc/";
  3159. $result=$this->commonGenerateDocument($modelpath, $modele, $outputlangs, $hidedetails, $hidedesc, $hideref, $moreparams);
  3160. }
  3161. return $result;
  3162. }
  3163. /**
  3164. * Sets object to supplied categories.
  3165. *
  3166. * Deletes object from existing categories not supplied.
  3167. * Adds it to non existing supplied categories.
  3168. * Existing categories are left untouch.
  3169. *
  3170. * @param int[]|int $categories Category or categories IDs
  3171. * @param string $type Category type (customer or supplier)
  3172. */
  3173. public function setCategories($categories, $type)
  3174. {
  3175. require_once DOL_DOCUMENT_ROOT . '/categories/class/categorie.class.php';
  3176. // Decode type
  3177. if ($type == 'customer') {
  3178. $type_id = Categorie::TYPE_CUSTOMER;
  3179. $type_text = 'customer';
  3180. } elseif ($type == 'supplier') {
  3181. $type_id = Categorie::TYPE_SUPPLIER;
  3182. $type_text = 'supplier';
  3183. } else {
  3184. dol_syslog(__METHOD__ . ': Type ' . $type . 'is an unknown company category type. Done nothing.', LOG_ERR);
  3185. return;
  3186. }
  3187. // Handle single category
  3188. if (!is_array($categories)) {
  3189. $categories = array($categories);
  3190. }
  3191. // Get current categories
  3192. $c = new Categorie($this->db);
  3193. $existing = $c->containing($this->id, $type_id, 'id');
  3194. // Diff
  3195. if (is_array($existing)) {
  3196. $to_del = array_diff($existing, $categories);
  3197. $to_add = array_diff($categories, $existing);
  3198. } else {
  3199. $to_del = array(); // Nothing to delete
  3200. $to_add = $categories;
  3201. }
  3202. // Process
  3203. foreach ($to_del as $del) {
  3204. if ($c->fetch($del) > 0) {
  3205. $c->del_type($this, $type_text);
  3206. }
  3207. }
  3208. foreach ($to_add as $add) {
  3209. if ($c->fetch($add) > 0) {
  3210. $c->add_type($this, $type_text);
  3211. }
  3212. }
  3213. return;
  3214. }
  3215. /**
  3216. * Function used to replace a thirdparty id with another one.
  3217. * It must be used within a transaction to avoid trouble
  3218. *
  3219. * @param DoliDB $db Database handler
  3220. * @param int $origin_id Old thirdparty id
  3221. * @param int $dest_id New thirdparty id
  3222. * @return bool
  3223. */
  3224. public static function replaceThirdparty(DoliDB $db, $origin_id, $dest_id)
  3225. {
  3226. /**
  3227. * Thirdparty commercials cannot be the same in both thirdparties so we look for them and remove some
  3228. * Because this function is meant to be executed within a transaction, we won't take care of it.
  3229. */
  3230. $sql = 'SELECT rowid FROM '.MAIN_DB_PREFIX.'societe_commerciaux ';
  3231. $sql .= ' WHERE fk_soc = '.(int) $dest_id.' AND fk_user IN ( ';
  3232. $sql .= ' SELECT fk_user ';
  3233. $sql .= ' FROM '.MAIN_DB_PREFIX.'societe_commerciaux ';
  3234. $sql .= ' WHERE fk_soc = '.(int) $origin_id.') ';
  3235. $query = $db->query($sql);
  3236. while ($result = $db->fetch_object($query)) {
  3237. $db->query('DELETE FROM '.MAIN_DB_PREFIX.'societe_commerciaux WHERE rowid = '.$result->rowid);
  3238. }
  3239. /**
  3240. * llx_societe_extrafields table must not be here because we don't care about the old thirdparty data
  3241. * Do not include llx_societe because it will be replaced later
  3242. */
  3243. $tables = array(
  3244. 'societe_address',
  3245. 'societe_commerciaux',
  3246. 'societe_log',
  3247. 'societe_prices',
  3248. 'societe_remise',
  3249. 'societe_remise_except',
  3250. 'societe_rib'
  3251. );
  3252. return CommonObject::commonReplaceThirdparty($db, $origin_id, $dest_id, $tables);
  3253. }
  3254. }