Refactored custom field option config pages.
[timetracker.git] / plugins / CustomFields.class.php
1 <?php
2 // +----------------------------------------------------------------------+
3 // | Anuko Time Tracker
4 // +----------------------------------------------------------------------+
5 // | Copyright (c) Anuko International Ltd. (https://www.anuko.com)
6 // +----------------------------------------------------------------------+
7 // | LIBERAL FREEWARE LICENSE: This source code document may be used
8 // | by anyone for any purpose, and freely redistributed alone or in
9 // | combination with other software, provided that the license is obeyed.
10 // |
11 // | There are only two ways to violate the license:
12 // |
13 // | 1. To redistribute this code in source form, with the copyright
14 // |    notice or license removed or altered. (Distributing in compiled
15 // |    forms without embedded copyright notices is permitted).
16 // |
17 // | 2. To redistribute modified versions of this code in *any* form
18 // |    that bears insufficient indications that the modifications are
19 // |    not the work of the original author(s).
20 // |
21 // | This license applies to this document only, not any other software
22 // | that it may be combined with.
23 // |
24 // +----------------------------------------------------------------------+
25 // | Contributors:
26 // | https://www.anuko.com/time_tracker/credits.htm
27 // +----------------------------------------------------------------------+
28
29 class CustomFields {
30
31   // Definitions of custom field types.
32
33   const TYPE_TEXT = 1;     // A text field.
34   const TYPE_DROPDOWN = 2; // A dropdown field with pre-defined values.
35
36   var $fields = array();  // Array of custom fields for group.
37   var $options = array(); // Array of options for a dropdown custom field.
38
39   // Constructor.
40   function __construct() {
41     global $user;
42     $mdb2 = getConnection();
43
44     $group_id = $user->getGroup();
45     $org_id = $user->org_id;
46
47     // Get fields.
48     $sql = "select id, type, label, required from tt_custom_fields".
49       " where group_id = $group_id and org_id = $org_id and status = 1 and type > 0";
50     $res = $mdb2->query($sql);
51     if (!is_a($res, 'PEAR_Error')) {
52       while ($val = $res->fetchRow()) {
53         $this->fields[] = array('id'=>$val['id'],'type'=>$val['type'],'label'=>$val['label'],'required'=>$val['required'],'value'=>'');
54       }
55     }
56
57     // If we have a dropdown obtain options for it.
58     if ((count($this->fields) > 0) && ($this->fields[0]['type'] == CustomFields::TYPE_DROPDOWN)) {
59
60       $sql = "select id, value from tt_custom_field_options".
61         " where field_id = ".$this->fields[0]['id']." and group_id = $group_id and org_id = $org_id and status = 1 order by value";
62       $res = $mdb2->query($sql);
63       if (!is_a($res, 'PEAR_Error')) {
64         while ($val = $res->fetchRow()) {
65           $this->options[$val['id']] = $val['value'];
66         }
67       }
68     }
69   }
70
71   function insert($log_id, $field_id, $option_id, $value) {
72     global $user;
73     $mdb2 = getConnection();
74
75     $group_id = $user->getGroup();
76     $org_id = $user->org_id;
77
78     $sql = "insert into tt_custom_field_log (group_id, org_id, log_id, field_id, option_id, value)".
79       " values($group_id, $org_id, $log_id, $field_id, ".$mdb2->quote($option_id).", ".$mdb2->quote($value).")";
80     $affected = $mdb2->exec($sql);
81     return (!is_a($affected, 'PEAR_Error'));
82   }
83
84   function update($log_id, $field_id, $option_id, $value) {
85     if (!$field_id)
86       return true; // Nothing to update.
87
88     // Remove older custom field values, if any.
89     $res = $this->delete($log_id);
90     if (!$res)
91       return false;
92
93     if (!$value && !$option_id)
94       return true; // Do not insert NULL values.
95
96     return $this->insert($log_id, $field_id, $option_id, $value);
97   }
98
99   function delete($log_id) {
100     global $user;
101     $mdb2 = getConnection();
102
103     $group_id = $user->getGroup();
104     $org_id = $user->org_id;
105
106     $sql = "update tt_custom_field_log set status = null".
107       " where log_id = $log_id and group_id = $group_id and org_id = $org_id";
108     $affected = $mdb2->exec($sql);
109     return (!is_a($affected, 'PEAR_Error'));
110   }
111
112   function get($log_id) {
113     global $user;
114     $mdb2 = getConnection();
115
116     $group_id = $user->getGroup();
117     $org_id = $user->org_id;
118
119     $sql = "select id, field_id, option_id, value from tt_custom_field_log".
120       " where log_id = $log_id and group_id = $group_id and org_id = $org_id and status = 1";
121     $res = $mdb2->query($sql);
122     if (!is_a($res, 'PEAR_Error')) {
123       $fields = array();
124       while ($val = $res->fetchRow()) {
125         $fields[] = $val;
126       }
127       return $fields;
128     }
129     return false;
130   }
131
132   // insertOption adds a new option to a custom field.
133   static function insertOption($field_id, $option_name) {
134     global $user;
135     $mdb2 = getConnection();
136
137     $group_id = $user->getGroup();
138     $org_id = $user->org_id;
139
140     // Check if the option exists.
141     $id = 0;
142     $sql = "select id from tt_custom_field_options".
143       " where field_id = $field_id and group_id = $group_id and org_id = $org_id and value = ".$mdb2->quote($option_name);
144     $res = $mdb2->query($sql);
145     if (is_a($res, 'PEAR_Error'))
146       return false;
147     if ($val = $res->fetchRow()) $id = $val['id'];
148
149     // Insert option.
150     if (!$id) {
151       $sql = "insert into tt_custom_field_options (group_id, org_id, field_id, value)".
152         " values($group_id, $org_id, $field_id, ".$mdb2->quote($option_name).")";
153       $affected = $mdb2->exec($sql);
154       if (is_a($affected, 'PEAR_Error'))
155         return false;
156     }
157     return true;
158   }
159
160   // updateOption updates option name.
161   static function updateOption($id, $option_name) {
162     global $user;
163     $mdb2 = getConnection();
164
165     $group_id = $user->getGroup();
166     $org_id = $user->org_id;
167
168     $sql = "update tt_custom_field_options set value = ".$mdb2->quote($option_name).
169        " where id = $id and group_id = $group_id and org_id = $org_id";
170     $affected = $mdb2->exec($sql);
171     return (!is_a($affected, 'PEAR_Error'));
172   }
173
174   // delete Option deletes an option and all custom field log entries that used it.
175   static function deleteOption($id) {
176     global $user;
177     $mdb2 = getConnection();
178
179     $group_id = $user->getGroup();
180     $org_id = $user->org_id;
181
182     $field_id = CustomFields::getFieldIdForOption($id);
183     if (!$field_id) return false;
184
185     // Delete log entries with this option. TODO: why? Research impact.
186     $sql = "update tt_custom_field_log set status = null".
187       " where field_id = $field_id and group_id = $group_id and org_id = $org_id and value = ".$mdb2->quote($id);
188     $affected = $mdb2->exec($sql);
189     if (is_a($affected, 'PEAR_Error'))
190       return false;
191
192     // Delete the option.
193     $sql = "update tt_custom_field_options set status = null".
194       " where id = $id and group_id = $group_id and org_id = $org_id";
195     $affected = $mdb2->exec($sql);
196     return (!is_a($affected, 'PEAR_Error'));
197   }
198
199   // getOptions returns an array of options for a custom field.
200   static function getOptions($field_id) {
201     global $user;
202     $mdb2 = getConnection();
203
204     $group_id = $user->getGroup();
205     $org_id = $user->org_id;
206
207     // Get options.
208     $sql = "select id, value from tt_custom_field_options".
209       " where field_id = $field_id and group_id = $group_id and org_id = $org_id and status = 1 order by value";
210     $res = $mdb2->query($sql);
211     if (!is_a($res, 'PEAR_Error')) {
212       $options = array();
213       while ($val = $res->fetchRow()) {
214         $options[$val['id']] = $val['value'];
215       }
216       return $options;
217     }
218     return false;
219   }
220
221   // getOptionName returns an option name for a custom field.
222   static function getOptionName($id) {
223     global $user;
224     $mdb2 = getConnection();
225
226     $group_id = $user->getGroup();
227     $org_id = $user->org_id;
228
229     $sql = "select value from tt_custom_field_options".
230       " where id = $id and group_id = $group_id and org_id = $org_id and status = 1";
231     $res = $mdb2->query($sql);
232     if (!is_a($res, 'PEAR_Error')) {
233       $val = $res->fetchRow();
234       $name = $val['value'];
235       return $name;
236     }
237     return false;
238   }
239
240   // getFields returns an array of custom fields for group.
241   static function getFields() {
242     global $user;
243     $mdb2 = getConnection();
244
245     $group_id = $user->getGroup();
246     $org_id = $user->org_id;
247
248     $fields = array();
249     $sql = "select id, type, label from tt_custom_fields".
250       " where group_id = $group_id and org_id = $org_id and status = 1 and type > 0";
251     $res = $mdb2->query($sql);
252     if (!is_a($res, 'PEAR_Error')) {
253       while ($val = $res->fetchRow()) {
254         $fields[] = array('id'=>$val['id'],'type'=>$val['type'],'label'=>$val['label']);
255       }
256       return $fields;
257     }
258     return false;
259   }
260
261   // getField returns a custom field.
262   static function getField($id) {
263     global $user;
264     $mdb2 = getConnection();
265
266     $group_id = $user->getGroup();
267     $org_id = $user->org_id;
268
269     $sql = "select label, type, required from tt_custom_fields".
270       " where id = $id and group_id = $group_id and org_id = $org_id";
271     $res = $mdb2->query($sql);
272     if (!is_a($res, 'PEAR_Error')) {
273       $val = $res->fetchRow();
274       if (!$val)
275         return false;
276       return $val;
277     }
278     return false;
279   }
280
281   // getFieldIdForOption returns field id from an associated option id.
282   static function getFieldIdForOption($option_id) {
283     global $user;
284     $mdb2 = getConnection();
285
286     $group_id = $user->getGroup();
287     $org_id = $user->org_id;
288
289     $sql = "select field_id from tt_custom_field_options".
290       " where id = $option_id and group_id = $group_id and org_id = $org_id";
291     $res = $mdb2->query($sql);
292     if (!is_a($res, 'PEAR_Error')) {
293       $val = $res->fetchRow();
294       $field_id = $val['field_id'];
295       return $field_id;
296     }
297     return false;
298   }
299
300   // The insertField inserts a custom field for group.
301   static function insertField($field_name, $field_type, $required) {
302     global $user;
303     $mdb2 = getConnection();
304
305     $group_id = $user->getGroup();
306     $org_id = $user->org_id;
307
308     $sql = "insert into tt_custom_fields (group_id, org_id, type, label, required, status)".
309       " values($group_id, $org_id, $field_type, ".$mdb2->quote($field_name).", $required, 1)";
310     $affected = $mdb2->exec($sql);
311     return (!is_a($affected, 'PEAR_Error'));
312   }
313
314   // The updateField updates custom field for group.
315   static function updateField($id, $name, $type, $required) {
316     global $user;
317     $mdb2 = getConnection();
318
319     $group_id = $user->getGroup();
320     $org_id = $user->org_id;
321
322     $sql = "update tt_custom_fields set label = ".$mdb2->quote($name).", type = $type, required = $required".
323       " where id = $id and group_id = $group_id and org_id = $org_id";
324     $affected = $mdb2->exec($sql);
325     return (!is_a($affected, 'PEAR_Error'));
326   }
327
328   // The deleteField deletes a custom field, its options and log entries for group.
329   static function deleteField($field_id) {
330     global $user;
331     $mdb2 = getConnection();
332
333     $group_id = $user->getGroup();
334     $org_id = $user->org_id;
335
336     // Mark log entries as deleted. TODO: why are we doing this? Research impact.
337     $sql = "update tt_custom_field_log set status = null".
338       " where field_id = $field_id and group_id = $group_id and org_id = $org_id";
339     $affected = $mdb2->exec($sql);
340     if (is_a($affected, 'PEAR_Error'))
341       return false;
342
343     // Mark field options as deleted.
344     $sql = "update tt_custom_field_options set status = null".
345       " where field_id = $field_id and group_id = $group_id and org_id = $org_id";
346     $affected = $mdb2->exec($sql);
347     if (is_a($affected, 'PEAR_Error'))
348       return false;
349
350     // Mark custom field as deleted.
351     $sql = "update tt_custom_fields set status = null".
352       " where id = $field_id and group_id = $group_id and org_id = $org_id";
353     $affected = $mdb2->exec($sql);
354     return (!is_a($affected, 'PEAR_Error'));
355   }
356 }