Cost handling in purchasing module fixed.
[fa-stable.git] / taxes / tax_rules.inc
1 <?php
2 /**********************************************************************
3     Copyright (C) FrontAccounting, LLC.
4         Released under the terms of the GNU General Public License, GPL, 
5         as published by the Free Software Foundation, either version 3 
6         of the License, or (at your option) any later version.
7     This program is distributed in the hope that it will be useful,
8     but WITHOUT ANY WARRANTY; without even the implied warranty of
9     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  
10     See the License here <http://www.gnu.org/licenses/gpl-3.0.html>.
11 ***********************************************************************/
12 /*
13         FA tax rules basic reimplementation. Final version would involve changes in database scheme,
14         and/or tax system class selection according to site requirements.
15
16         TODO:
17         . changes in Sales module
18         . change all tax related methods in supp_trans to use split_item_price instead of other functions like get_taxes_for_item
19 */
20 define('TAX_NONE', 0); // none option
21 define('TQ_NONE', 0); // none option
22
23 // implemented taxation options
24 // basic:
25 define('TAX_PAYABLE', 1);
26 define('TAX_DEDUCTIBLE', 2);
27 define('TAX_CHARGED', 4);
28 // category depenedent:
29 define('TAX_DUEDATE', 8);
30 define('TAX_PARTIAL', 16);
31
32 // quirks dependent on vat_categories
33 define('TQ_NONDEDUCT', 1);      // never deductible
34 define('TQ_PARTIAL', 2);        // partially deductible (using global factor)
35 define('TQ_DUEDATE', 4);        // taxable on due date instead of transaction date
36 define('TQ_REVERSE', 8);        // tax is reverse charged
37 define('TQ_IMPDEDUCTIBLE', 16); // import tax is deductible
38
39 class tax_system
40 {
41         //-------------------------- entity taxation rules ----------------------------
42         // general rules: who and when pays taxes
43         //
44         // FIXME: credit notes
45         //
46         var     $description;
47         var $ts_basic_rules;
48         var $ts_category_quirks;
49
50         function __construct()
51         {
52                 $this->ts_basic_rules = array(
53                         TA_DOMESTIC => array(
54                                 ST_SALESQUOTE => TAX_CHARGED,
55                                 ST_SALESORDER => TAX_CHARGED,
56                                 ST_CUSTDELIVERY => TAX_CHARGED,
57                                 ST_SALESINVOICE => TAX_PAYABLE | TAX_CHARGED,
58                                 ST_CUSTCREDIT => TAX_PAYABLE | TAX_CHARGED,
59                                 ST_PURCHORDER => TAX_CHARGED,
60                                 ST_SUPPRECEIVE => TAX_CHARGED,
61                                 ST_SUPPINVOICE => TAX_DEDUCTIBLE | TAX_CHARGED,
62                                 ST_SUPPCREDIT => TAX_DEDUCTIBLE | TAX_CHARGED,
63                         ),
64                         TA_EXPORT => array(
65                                 ST_SALESQUOTE => TAX_NONE,
66                                 ST_SALESORDER => TAX_NONE,
67                                 ST_CUSTDELIVERY => TAX_NONE,
68                                 ST_SALESINVOICE => TAX_NONE,
69                                 ST_CUSTCREDIT => TAX_NONE,
70                                 ST_PURCHORDER => TAX_NONE,
71                                 ST_SUPPRECEIVE => TAX_NONE,
72                                 ST_SUPPINVOICE => TAX_NONE,
73                                 ST_SUPPCREDIT => TAX_NONE,
74                         ),
75                         TA_EU => array(
76                                 ST_SALESQUOTE => TAX_NONE,
77                                 ST_SALESORDER => TAX_NONE,
78                                 ST_CUSTDELIVERY => TAX_NONE,
79                                 ST_SALESINVOICE => TAX_NONE,
80                                 ST_CUSTCREDIT => TAX_NONE,
81                                 ST_PURCHORDER => TAX_NONE,
82                                 ST_SUPPRECEIVE => TAX_NONE,
83                                 ST_SUPPINVOICE => TAX_DEDUCTIBLE | TAX_PAYABLE,
84                                 ST_SUPPCREDIT => TAX_DEDUCTIBLE | TAX_PAYABLE,
85                         ),
86                 );
87
88                 //-------------------------- special goods dependent rules  ----------------------------
89                 //
90                 $this->ts_category_quirks = array(
91                         VC_OTHER => TQ_NONE,
92                         VC_MEDIA => TQ_DUEDATE,                 // is no longer used ?
93                         VC_ASSETS => TQ_NONE,                   // just separate category in tax reg
94                         VC_NONDEDUCT => TQ_NONDEDUCT,
95                         VC_SERVICES => TQ_IMPDEDUCTIBLE,
96                         VC_PARTIAL => TQ_PARTIAL,
97                         VC_REVERSE => TQ_REVERSE,
98                 );
99         }
100         /*
101                 Returns tax options applicable for the arguments set
102
103                 $allow_reverse - decides whether reverse charging option is honoured for sales invoice
104                 (this depends on 'continue transaction' value as defined by law, so have to be set by case).
105         */
106         function options($trans_type, $tax_area, $vat_category, $allow_reverse=true)
107         {
108                 if (!isset($vat_category)) // exempt goods has really no category
109                         return TAX_NONE;
110
111                 $options = $this->ts_basic_rules[$tax_area][$trans_type];
112
113                 // per vat category quirks
114                 $quirks = $this->ts_category_quirks[$vat_category];
115
116                 if ($quirks & TQ_DUEDATE)
117                         $options |= TAX_DUEDATE;
118
119                 if ($quirks & TQ_NONDEDUCT)
120                         $options &= ~TAX_DEDUCTIBLE;
121
122                 if ($quirks & TQ_PARTIAL)
123                         if ($options & TAX_DEDUCTIBLE)
124                                 $options |= TAX_PARTIAL;
125
126                 if ($quirks & TQ_IMPDEDUCTIBLE)
127                         if ($tax_area == TA_EXPORT && in_array($trans_type, array(ST_SUPPINVOICE, ST_SUPPCREDIT)))
128                         {
129                                 $options |= TAX_DEDUCTIBLE | TAX_PAYABLE;
130                         }
131
132                 if (($quirks & TQ_REVERSE) && (!in_array($trans_type,array(ST_SALESINVOICE, ST_CUSTCREDIT)) || $allow_reverse))
133                         if ($tax_area == TA_DOMESTIC)
134                         {
135                                 $options ^= TAX_PAYABLE;
136                                 $options &= ~TAX_CHARGED;
137                         }
138
139                 return $options;
140         }
141 };
142
143 function dbg_tax($options)
144 {
145         $dbg_rules = array(
146                 TAX_PAYABLE => 'payable',
147                 TAX_DEDUCTIBLE => 'deductible',
148                 TAX_CHARGED => 'charged',
149                 TAX_DUEDATE => 'due_date',
150                 TAX_PARTIAL => 'partial'
151         );
152
153         $opts = array();
154         foreach($dbg_rules as $key => $name)
155                 if ($options & $key)
156                         $opts[] = $name;
157
158         _vd(implode($opts, ','));
159 }