summaryrefslogtreecommitdiff
path: root/LedgerSMB/HR.pm
blob: 455b2d1f103157d13f1b99c2901787633335bb1c (plain)
  1. #=====================================================================
  2. # LedgerSMB
  3. # Small Medium Business Accounting software
  4. #
  5. # Copyright (C) 2006
  6. # This work contains copyrighted information from a number of sources all used
  7. # with permission.
  8. #
  9. # This file contains source code included with or based on SQL-Ledger which
  10. # is Copyright Dieter Simader and DWS Systems Inc. 2000-2005 and licensed
  11. # under the GNU General Public License version 2 or, at your option, any later
  12. # version. For a full list including contact information of contributors,
  13. # maintainers, and copyright holders, see the CONTRIBUTORS file.
  14. #
  15. # Original Copyright Notice from SQL-Ledger 2.6.17 (before the fork):
  16. # Copyright (C) 2003
  17. #
  18. # Author: DWS Systems Inc.
  19. # Web: http://www.sql-ledger.org
  20. #
  21. # Contributors:
  22. #
  23. #======================================================================
  24. #
  25. # This file has NOT undergone whitespace cleanup.
  26. #
  27. #======================================================================
  28. #
  29. # backend code for human resources and payroll
  30. #
  31. #======================================================================
  32. package HR;
  33. sub get_employee {
  34. my ($self, $myconfig, $form) = @_;
  35. my $dbh = $form->dbconnect($myconfig);
  36. my $query;
  37. my $sth;
  38. my $ref;
  39. my $notid = "";
  40. if ($form->{id}) {
  41. $query = qq|SELECT e.*
  42. FROM employee e
  43. WHERE e.id = $form->{id}|;
  44. $sth = $dbh->prepare($query);
  45. $sth->execute || $form->dberror($query);
  46. $ref = $sth->fetchrow_hashref(NAME_lc);
  47. # check if employee can be deleted, orphaned
  48. $form->{status} = "orphaned" unless $ref->{login};
  49. $form->{status} = 'orphaned'; # leave orphaned for now until payroll is done
  50. $ref->{employeelogin} = $ref->{login};
  51. delete $ref->{login};
  52. for (keys %$ref) { $form->{$_} = $ref->{$_} }
  53. $sth->finish;
  54. # get manager
  55. $form->{managerid} *= 1;
  56. $query = qq|SELECT name
  57. FROM employee
  58. WHERE id = $form->{managerid}|;
  59. ($form->{manager}) = $dbh->selectrow_array($query);
  60. ######### disabled for now
  61. if ($form->{deductions}) {
  62. # get allowances
  63. $query = qq|SELECT d.id, d.description, da.before, da.after, da.rate
  64. FROM employeededuction da
  65. JOIN deduction d ON (da.deduction_id = d.id)
  66. WHERE da.employee_id = $form->{id}|;
  67. $sth = $dbh->prepare($query);
  68. $sth->execute || $form->dberror($query);
  69. while ($ref = $sth->fetchrow_hashref(NAME_lc)) {
  70. $ref->{rate} *= 100;
  71. push @{ $form->{all_employeededuction} }, $ref;
  72. }
  73. $sth->finish;
  74. }
  75. $notid = qq|AND id != $form->{id}|;
  76. } else {
  77. $query = qq|SELECT current_date FROM defaults|;
  78. ($form->{startdate}) = $dbh->selectrow_array($query);
  79. }
  80. # get managers
  81. $query = qq|SELECT id, name
  82. FROM employee
  83. WHERE sales = '1'
  84. AND role = 'manager'
  85. $notid
  86. ORDER BY 2|;
  87. $sth = $dbh->prepare($query);
  88. $sth->execute || $form->dberror($query);
  89. while ($ref = $sth->fetchrow_hashref(NAME_lc)) {
  90. push @{ $form->{all_manager} }, $ref;
  91. }
  92. $sth->finish;
  93. # get deductions
  94. if ($form->{deductions}) {
  95. $query = qq|SELECT id, description
  96. FROM deduction
  97. ORDER BY 2|;
  98. $sth = $dbh->prepare($query);
  99. $sth->execute || $form->dberror($query);
  100. while ($ref = $sth->fetchrow_hashref(NAME_lc)) {
  101. push @{ $form->{all_deduction} }, $ref;
  102. }
  103. $sth->finish;
  104. }
  105. $dbh->disconnect;
  106. }
  107. sub save_employee {
  108. my ($self, $myconfig, $form) = @_;
  109. # connect to database
  110. my $dbh = $form->dbconnect_noauto($myconfig);
  111. my $query;
  112. my $sth;
  113. if (! $form->{id}) {
  114. my $uid = localtime;
  115. $uid .= "$$";
  116. $query = qq|INSERT INTO employee (name)
  117. VALUES ('$uid')|;
  118. $dbh->do($query) || $form->dberror($query);
  119. $query = qq|SELECT id FROM employee
  120. WHERE name = '$uid'|;
  121. $sth = $dbh->prepare($query);
  122. $sth->execute || $form->dberror($query);
  123. ($form->{id}) = $sth->fetchrow_array;
  124. $sth->finish;
  125. }
  126. my ($null, $managerid) = split /--/, $form->{manager};
  127. $managerid *= 1;
  128. $form->{sales} *= 1;
  129. $form->{employeenumber} = $form->update_defaults($myconfig, "employeenumber", $dbh) if ! $form->{employeenumber};
  130. $query = qq|UPDATE employee SET
  131. employeenumber = |.$dbh->quote($form->{employeenumber}).qq|,
  132. name = |.$dbh->quote($form->{name}).qq|,
  133. address1 = |.$dbh->quote($form->{address1}).qq|,
  134. address2 = |.$dbh->quote($form->{address2}).qq|,
  135. city = |.$dbh->quote($form->{city}).qq|,
  136. state = |.$dbh->quote($form->{state}).qq|,
  137. zipcode = |.$dbh->quote($form->{zipcode}).qq|,
  138. country = |.$dbh->quote($form->{country}).qq|,
  139. workphone = '$form->{workphone}',
  140. homephone = '$form->{homephone}',
  141. startdate = |.$form->dbquote($form->{startdate}, SQL_DATE).qq|,
  142. enddate = |.$form->dbquote($form->{enddate}, SQL_DATE).qq|,
  143. notes = |.$dbh->quote($form->{notes}).qq|,
  144. role = '$form->{role}',
  145. sales = '$form->{sales}',
  146. email = |.$dbh->quote($form->{email}).qq|,
  147. ssn = '$form->{ssn}',
  148. dob = |.$form->dbquote($form->{dob}, SQL_DATE).qq|,
  149. iban = '$form->{iban}',
  150. bic = '$form->{bic}',
  151. managerid = $managerid
  152. WHERE id = $form->{id}|;
  153. $dbh->do($query) || $form->dberror($query);
  154. # for now
  155. if ($form->{selectdeduction}) {
  156. # insert deduction and allowances for payroll
  157. $query = qq|DELETE FROM employeededuction
  158. WHERE employee_id = $form->{id}|;
  159. $dbh->do($query) || $form->dberror($query);
  160. $query = qq|INSERT INTO employeededuction (employee_id, deduction_id,
  161. before, after, rate) VALUES ($form->{id},?,?,?,?)|;
  162. my $sth = $dbh->prepare($query) || $form->dberror($query);
  163. for ($i = 1; $i <= $form->{deduction_rows}; $i++) {
  164. for (qw(before after)) { $form->{"${_}_$i"} = $form->parse_amount($myconfig, $form->{"${_}_$i"}) }
  165. ($null, $deduction_id) = split /--/, $form->{"deduction_$i"};
  166. if ($deduction_id) {
  167. $sth->execute($deduction_id, $form->{"before_$i"}, $form->{"after_$i"}, $form->{"rate_$i"} / 100) || $form->dberror($query);
  168. }
  169. }
  170. $sth->finish;
  171. }
  172. $dbh->commit;
  173. $dbh->disconnect;
  174. }
  175. sub delete_employee {
  176. my ($self, $myconfig, $form) = @_;
  177. # connect to database
  178. my $dbh = $form->dbconnect_noauto($myconfig);
  179. # delete employee
  180. my $query = qq|DELETE FROM $form->{db}
  181. WHERE id = $form->{id}|;
  182. $dbh->do($query) || $form->dberror($query);
  183. $dbh->commit;
  184. $dbh->disconnect;
  185. }
  186. sub employees {
  187. my ($self, $myconfig, $form) = @_;
  188. # connect to database
  189. my $dbh = $form->dbconnect($myconfig);
  190. my $where = "1 = 1";
  191. $form->{sort} = ($form->{sort}) ? $form->{sort} : "name";
  192. my @a = qw(name);
  193. my $sortorder = $form->sort_order(\@a);
  194. my $var;
  195. if ($form->{startdatefrom}) {
  196. $where .= " AND e.startdate >= '$form->{startdatefrom}'";
  197. }
  198. if ($form->{startdateto}) {
  199. $where .= " AND e.startddate <= '$form->{startdateto}'";
  200. }
  201. if ($form->{name} ne "") {
  202. $var = $form->like(lc $form->{name});
  203. $where .= " AND lower(e.name) LIKE '$var'";
  204. }
  205. if ($form->{notes} ne "") {
  206. $var = $form->like(lc $form->{notes});
  207. $where .= " AND lower(e.notes) LIKE '$var'";
  208. }
  209. if ($form->{sales} eq 'Y') {
  210. $where .= " AND e.sales = '1'";
  211. }
  212. if ($form->{status} eq 'orphaned') {
  213. $where .= qq| AND e.login IS NULL|;
  214. }
  215. if ($form->{status} eq 'active') {
  216. $where .= qq| AND e.enddate IS NULL|;
  217. }
  218. if ($form->{status} eq 'inactive') {
  219. $where .= qq| AND e.enddate <= current_date|;
  220. }
  221. my $query = qq|SELECT e.*, m.name AS manager
  222. FROM employee e
  223. LEFT JOIN employee m ON (m.id = e.managerid)
  224. WHERE $where
  225. ORDER BY $sortorder|;
  226. my $sth = $dbh->prepare($query);
  227. $sth->execute || $form->dberror($query);
  228. while (my $ref = $sth->fetchrow_hashref(NAME_lc)) {
  229. $ref->{address} = "";
  230. for (qw(address1 address2 city state zipcode country)) { $ref->{address} .= "$ref->{$_} " }
  231. push @{ $form->{all_employee} }, $ref;
  232. }
  233. $sth->finish;
  234. $dbh->disconnect;
  235. }
  236. sub get_deduction {
  237. my ($self, $myconfig, $form) = @_;
  238. my $dbh = $form->dbconnect($myconfig);
  239. my $query;
  240. my $sth;
  241. my $ref;
  242. my $item;
  243. my $i;
  244. if ($form->{id}) {
  245. $query = qq|SELECT d.*,
  246. c1.accno AS ap_accno,
  247. c1.description AS ap_description,
  248. c2.accno AS expense_accno,
  249. c2.description AS expense_description
  250. FROM deduction d
  251. LEFT JOIN chart c1 ON (c1.id = d.ap_accno_id)
  252. LEFT JOIN chart c2 ON (c2.id = d.expense_accno_id)
  253. WHERE d.id = $form->{id}|;
  254. $sth = $dbh->prepare($query);
  255. $sth->execute || $form->dberror($query);
  256. $ref = $sth->fetchrow_hashref(NAME_lc);
  257. for (keys %$ref) { $form->{$_} = $ref->{$_} }
  258. $sth->finish;
  259. # check if orphaned
  260. $form->{status} = 'orphaned'; # for now
  261. # get the rates
  262. $query = qq|SELECT rate, amount, above, below
  263. FROM deductionrate
  264. WHERE trans_id = $form->{id}
  265. ORDER BY rate, amount|;
  266. $sth = $dbh->prepare($query);
  267. $sth->execute || $form->dberror($query);
  268. while ($ref = $sth->fetchrow_hashref(NAME_lc)) {
  269. push @{ $form->{deductionrate} }, $ref;
  270. }
  271. $sth->finish;
  272. # get all for deductionbase
  273. $query = qq|SELECT d.description, d.id, db.maximum
  274. FROM deductionbase db
  275. JOIN deduction d ON (d.id = db.deduction_id)
  276. WHERE db.trans_id = $form->{id}|;
  277. $sth = $dbh->prepare($query);
  278. $sth->execute || $form->dberror($query);
  279. while ($ref = $sth->fetchrow_hashref(NAME_lc)) {
  280. push @{ $form->{deductionbase} }, $ref;
  281. }
  282. $sth->finish;
  283. # get all for deductionafter
  284. $query = qq|SELECT d.description, d.id
  285. FROM deductionafter da
  286. JOIN deduction d ON (d.id = da.deduction_id)
  287. WHERE da.trans_id = $form->{id}|;
  288. $sth = $dbh->prepare($query);
  289. $sth->execute || $form->dberror($query);
  290. while ($ref = $sth->fetchrow_hashref(NAME_lc)) {
  291. push @{ $form->{deductionafter} }, $ref;
  292. }
  293. $sth->finish;
  294. # build selection list for base and after
  295. $query = qq|SELECT id, description
  296. FROM deduction
  297. WHERE id != $form->{id}
  298. ORDER BY 2|;
  299. } else {
  300. # build selection list for base and after
  301. $query = qq|SELECT id, description
  302. FROM deduction
  303. ORDER BY 2|;
  304. }
  305. $sth = $dbh->prepare($query);
  306. $sth->execute || $form->dberror($query);
  307. while ($ref = $sth->fetchrow_hashref(NAME_lc)) {
  308. push @{ $form->{all_deduction} }, $ref;
  309. }
  310. $sth->finish;
  311. my %category = ( ap => 'L',
  312. expense => 'E' );
  313. foreach $item (keys %category) {
  314. $query = qq|SELECT accno, description
  315. FROM chart
  316. WHERE charttype = 'A'
  317. AND category = '$category{$item}'
  318. ORDER BY accno|;
  319. $sth = $dbh->prepare($query);
  320. $sth->execute || $form->dberror($query);
  321. while ($ref = $sth->fetchrow_hashref(NAME_lc)) {
  322. push @{ $form->{"${item}_accounts"} }, $ref;
  323. }
  324. $sth->finish;
  325. }
  326. $dbh->disconnect;
  327. }
  328. sub deductions {
  329. my ($self, $myconfig, $form) = @_;
  330. my $dbh = $form->dbconnect($myconfig);
  331. my $query = qq|SELECT d.id, d.description, d.employeepays, d.employerpays,
  332. c1.accno AS ap_accno, c2.accno AS expense_accno,
  333. dr.rate, dr.amount, dr.above, dr.below
  334. FROM deduction d
  335. JOIN deductionrate dr ON (dr.trans_id = d.id)
  336. LEFT JOIN chart c1 ON (d.ap_accno_id = c1.id)
  337. LEFT JOIN chart c2 ON (d.expense_accno_id = c2.id)
  338. ORDER BY 2, 7, 8|;
  339. my $sth = $dbh->prepare($query);
  340. $sth->execute || $form->dberror($query);
  341. while (my $ref = $sth->fetchrow_hashref(NAME_lc)) {
  342. push @{ $form->{all_deduction} }, $ref;
  343. }
  344. $sth->finish;
  345. $dbh->disconnect;
  346. }
  347. sub save_deduction {
  348. my ($self, $myconfig, $form) = @_;
  349. # connect to database
  350. my $dbh = $form->dbconnect_noauto($myconfig);
  351. ($form->{ap_accno}) = split /--/, $form->{ap_accno};
  352. ($form->{expense_accno}) = split /--/, $form->{expense_accno};
  353. my $null;
  354. my $deduction_id;
  355. my $query;
  356. my $sth;
  357. if (! $form->{id}) {
  358. my $uid = localtime;
  359. $uid .= "$$";
  360. $query = qq|INSERT INTO deduction (description)
  361. VALUES ('$uid')|;
  362. $dbh->do($query) || $form->dberror($query);
  363. $query = qq|SELECT id FROM deduction
  364. WHERE description = '$uid'|;
  365. $sth = $dbh->prepare($query);
  366. $sth->execute || $form->dberror($query);
  367. ($form->{id}) = $sth->fetchrow_array;
  368. $sth->finish;
  369. }
  370. for (qw(employeepays employerpays)) { $form->{$_} = $form->parse_amount($myconfig, $form->{$_}) }
  371. $query = qq|UPDATE deduction SET
  372. description = |.$dbh->quote($form->{description}).qq|,
  373. ap_accno_id =
  374. (SELECT id FROM chart
  375. WHERE accno = '$form->{ap_accno}'),
  376. expense_accno_id =
  377. (SELECT id FROM chart
  378. WHERE accno = '$form->{expense_accno}'),
  379. employerpays = '$form->{employerpays}',
  380. employeepays = '$form->{employeepays}',
  381. fromage = |.$form->dbquote($form->{fromage}, SQL_INT).qq|,
  382. toage = |.$form->dbquote($form->{toage}, SQL_INT).qq|
  383. WHERE id = $form->{id}|;
  384. $dbh->do($query) || $form->dberror($query);
  385. $query = qq|DELETE FROM deductionrate
  386. WHERE trans_id = $form->{id}|;
  387. $dbh->do($query) || $form->dberror($query);
  388. $query = qq|INSERT INTO deductionrate
  389. (trans_id, rate, amount, above, below) VALUES (?,?,?,?,?)|;
  390. $sth = $dbh->prepare($query) || $form->dberror($query);
  391. for ($i = 1; $i <= $form->{rate_rows}; $i++) {
  392. for (qw(rate amount above below)) { $form->{"${_}_$i"} = $form->parse_amount($myconfig, $form->{"${_}_$i"}) }
  393. $form->{"rate_$i"} /= 100;
  394. if ($form->{"rate_$i"} || $form->{"amount_$i"}) {
  395. $sth->execute($form->{id}, $form->{"rate_$i"}, $form->{"amount_$i"}, $form->{"above_$i"}, $form->{"below_$i"}) || $form->dberror($query);
  396. }
  397. }
  398. $sth->finish;
  399. $query = qq|DELETE FROM deductionbase
  400. WHERE trans_id = $form->{id}|;
  401. $dbh->do($query) || $form->dberror($query);
  402. $query = qq|INSERT INTO deductionbase
  403. (trans_id, deduction_id, maximum) VALUES (?,?,?)|;
  404. $sth = $dbh->prepare($query) || $form->dberror($query);
  405. for ($i = 1; $i <= $form->{base_rows}; $i++) {
  406. ($null, $deduction_id) = split /--/, $form->{"base_$i"};
  407. $form->{"maximum_$i"} = $form->parse_amount($myconfig, $form->{"maximum_$i"});
  408. if ($deduction_id) {
  409. $sth->execute($form->{id}, $deduction_id, $form->{"maximum_$i"}) || $form->dberror($query);
  410. }
  411. }
  412. $sth->finish;
  413. $query = qq|DELETE FROM deductionafter
  414. WHERE trans_id = $form->{id}|;
  415. $dbh->do($query) || $form->dberror($query);
  416. $query = qq|INSERT INTO deductionafter
  417. (trans_id, deduction_id) VALUES (?,?)|;
  418. $sth = $dbh->prepare($query) || $form->dberror($query);
  419. for ($i = 1; $i <= $form->{after_rows}; $i++) {
  420. ($null, $deduction_id) = split /--/, $form->{"after_$i"};
  421. if ($deduction_id) {
  422. $sth->execute($form->{id}, $deduction_id) || $form->dberror($query);
  423. }
  424. }
  425. $sth->finish;
  426. $dbh->commit;
  427. $dbh->disconnect;
  428. }
  429. sub delete_deduction {
  430. my ($self, $myconfig, $form) = @_;
  431. # connect to database
  432. my $dbh = $form->dbconnect_noauto($myconfig);
  433. # delete deduction
  434. my $query = qq|DELETE FROM $form->{db}
  435. WHERE id = $form->{id}|;
  436. $dbh->do($query) || $form->dberror($query);
  437. foreach $item (qw(rate base after)) {
  438. $query = qq|DELETE FROM deduction$item
  439. WHERE trans_id = $form->{id}|;
  440. $dbh->do($query) || $form->dberror($query);
  441. }
  442. $dbh->commit;
  443. $dbh->disconnect;
  444. }
  445. 1;