Update lua versions
[ryzomcore.git] / web / private_php / ams / autoload / ticket.php
bloba47a61659bf5f42e00b7c0e077feb1c0cd7d0c1d
1 <?php
3 /**
4 * class that handles most ticket related functions.
5 * the ticket class is used for most ticketing related functions, it also holds some wrapper functions.
6 * @author Daan Janssens, mentored by Matthew Lagoe
7 */
8 class Ticket{
10 private $tId; /**< The id of ticket */
11 private $timestamp; /**< Timestamp of the ticket */
12 private $title; /**< Title of the ticket */
13 private $status; /**< Status of the ticket (0 = waiting on user reply, 1 = waiting on support, (2= not used atm), 3 = closed */
14 private $queue; /**< (not in use atm) */
15 private $ticket_category; /**< the id of the category belonging to the ticket */
16 private $author; /**< The ticket_users id */
17 private $priority; /**< The priority of the ticket where 0 = low, 3= supadupahigh */
19 ////////////////////////////////////////////Functions////////////////////////////////////////////////////
22 /**
23 * check if a ticket exists.
24 * @param $id the id of the ticket to be checked.
25 * @return true if the ticket exists, else false.
27 public static function ticketExists($id) {
28 $dbl = new DBLayer("lib");
29 //check if ticket exists
30 if( $dbl->select("`ticket`", array('ticket_id' => $id), "`TId` = :ticket_id")->rowCount() ){
31 return true;
32 }else{
33 return false;
38 /**
39 * return an array of the possible statuses
40 * @return an array containing the string values that represent the different statuses.
42 public static function getStatusArray() {
43 return Array("Waiting on user reply","Waiting on support","Waiting on Dev reply","Closed");
47 /**
48 * return an array of the possible priorities
49 * @return an array containing the string values that represent the different priorities.
51 public static function getPriorityArray() {
52 return Array("Low","Normal","High","Super Dupa High");
56 /**
57 * return an entire ticket.
58 * returns the ticket object and an array of all replies to that ticket.
59 * @param $id the id of the ticket.
60 * @param $view_as_admin true if the viewer of the ticket is a mod, else false (depending on this it will also show the hidden comments)
61 * @return an array containing the 'ticket_obj' and a 'reply_array', which is an array containing all replies to that ticket.
63 public static function getEntireTicket($id,$view_as_admin) {
64 $ticket = new Ticket();
65 $ticket->load_With_TId($id);
66 $reply_array = Ticket_Reply::getRepliesOfTicket($id, $view_as_admin);
67 return Array('ticket_obj' => $ticket,'reply_array' => $reply_array);
71 /**
72 * return all tickets of a specific user.
73 * an array of all tickets created by a specific user are returned by this function.
74 * @param $author the id of the user of whom we want all tickets from.
75 * @return an array containing all ticket objects related to a user.
77 public static function getTicketsOf($author) {
78 $dbl = new DBLayer("lib");
79 $statement = $dbl->execute("SELECT * FROM ticket INNER JOIN ticket_user ON ticket.Author = ticket_user.TUserId and ticket_user.ExternId=:id", array('id' => $author));
80 $row = $statement->fetchAll();
81 $result = Array();
82 foreach($row as $ticket){
83 $instance = new self();
84 $instance->setTId($ticket['TId']);
85 $instance->setTimestamp($ticket['Timestamp']);
86 $instance->setTitle($ticket['Title']);
87 $instance->setStatus($ticket['Status']);
88 $instance->setQueue($ticket['Queue']);
89 $instance->setTicket_Category($ticket['Ticket_Category']);
90 $instance->setAuthor($ticket['Author']);
91 $result[] = $instance;
93 return $result;
98 /**
99 * function that creates a new ticket.
100 * A new ticket will be created, in case the extra_info != 0 and the http request came from ingame, then a ticket_info page will be created.
101 * A log entry will be written, depending on the $real_authors value. In case the for_support_group parameter is set, the ticket will be forwarded immediately.
102 * Also the mail handler will create a new email that will be sent to the author to notify him that his ticket is freshly created.
103 * @param $title the title we want to give to the ticket.
104 * @param $content the content we want to give to the starting post of the ticket.
105 * @param $category the id of the category that should be related to the ticket.
106 * @param $author the person who's id will be stored in the database as creator of the ticket.
107 * @param $real_author should be the same id, or a moderator/admin who creates a ticket for another user (this is used for logging purposes).
108 * @param $for_support_group in case you directly want to forward the ticket after creating it. (default value = 0 = don't forward)
109 * @param $extra_info used for creating an ticket_info page related to the ticket, this only happens when the ticket is made ingame.
110 * @return the created tickets id.
112 public static function create_Ticket( $title, $content, $category, $author, $real_author, $for_support_group = 0, $extra_info = 0) {
114 //create the new ticket!
115 $ticket = new Ticket();
116 $values = array("Title" => $title, "Timestamp"=>0, "Status"=> 1, "Queue"=> 0, "Ticket_Category" => $category, "Author" => $author, "Priority" => 0);
117 $ticket->set($values);
118 $ticket->create();
119 $ticket_id = $ticket->getTId();
121 //if ingame then add an extra info
122 if(Helpers::check_if_game_client() && $extra_info != 0){
123 $extra_info['Ticket'] = $ticket_id;
124 Ticket_Info::create_Ticket_Info($extra_info);
127 //write a log entry
128 if ( $author == $real_author){
129 Ticket_Log::createLogEntry( $ticket_id, $author, 1);
130 }else{
131 Ticket_Log::createLogEntry( $ticket_id, $real_author, 2, $author);
133 Ticket_Reply::createReply($content, $author, $ticket_id, 0, $author);
135 //forwards the ticket directly after creation to the supposed support group
136 if($for_support_group){
137 Ticket::forwardTicket(0, $ticket_id, $for_support_group);
140 //send email that new ticket has been created
141 Mail_Handler::send_ticketing_mail($ticket->getAuthor(), $ticket, $content, "NEW", $ticket->getForwardedGroupId());
142 return $ticket_id;
148 * updates the ticket's status.
149 * A log entry about this will be created only if the newStatus is different from the current status.
150 * @param $ticket_id the id of the ticket of which we want to change the status.
151 * @param $newStatus the new status value (integer)
152 * @param $author the user (id) that performed the update status action
154 public static function updateTicketStatus( $ticket_id, $newStatus, $author) {
156 $ticket = new Ticket();
157 $ticket->load_With_TId($ticket_id);
158 if ($ticket->getStatus() != $newStatus){
159 $ticket->setStatus($newStatus);
160 Ticket_Log::createLogEntry( $ticket_id, $author, 5, $newStatus);
162 $ticket->update();
168 * updates the ticket's status & priority.
169 * A log entry about this will be created only if the newStatus is different from the current status and also when the newPriority is different from the current priority.
170 * @todo break this function up into a updateStatus (already exists) and updatePriority function and perhaps write a wrapper function for the combo.
171 * @param $ticket_id the id of the ticket of which we want to change the status & priority
172 * @param $newStatus the new status value (integer)
173 * @param $newPriority the new priority value (integer)
174 * @param $author the user (id) that performed the update
176 public static function updateTicketStatusAndPriority( $ticket_id, $newStatus, $newPriority, $author) {
178 $ticket = new Ticket();
179 $ticket->load_With_TId($ticket_id);
180 if ($ticket->getStatus() != $newStatus){
181 $ticket->setStatus($newStatus);
182 Ticket_Log::createLogEntry( $ticket_id, $author, 5, $newStatus);
184 if ($ticket->getPriority() != $newPriority){
185 $ticket->setPriority($newPriority);
186 Ticket_Log::createLogEntry( $ticket_id, $author, 6, $newPriority);
188 $ticket->update();
194 * return the latest reply of a ticket
195 * @param $ticket_id the id of the ticket.
196 * @return a ticket_reply object.
198 public static function getLatestReply( $ticket_id) {
199 $dbl = new DBLayer("lib");
200 $statement = $dbl->execute("SELECT * FROM ticket_reply WHERE Ticket =:id ORDER BY TReplyId DESC LIMIT 1 ", array('id' => $ticket_id));
201 $reply = new Ticket_Reply();
202 $reply->set($statement->fetch());
203 return $reply;
207 * return the attachments list
208 * @param $ticket_id the id of the ticket.
209 * @return a ticket_reply object.
211 public static function getAttachments( $ticket_id) {
212 $dbl = new DBLayer("lib");
213 $statement = $dbl->select("`ticket_attachments`",array('ticket_TId' => $ticket_id), "`ticket_TId` =:ticket_TId ORDER BY Timestamp DESC");
214 $fetchall = $statement->fetchall();
215 $base = 0;
216 foreach ($fetchall as &$value) {
217 $webUser = new WebUsers($value['Uploader']);
218 $fetchall[$base]['Username'] = $webUser->getUsername();
220 $bytes = $fetchall[$base]['Filesize'];
221 $precision = 2;
222 $units = array('B', 'KB', 'MB', 'GB', 'TB');
224 $bytes = max($bytes, 0);
225 $pow = floor(($bytes ? log($bytes) : 0) / log(1024));
226 $pow = min($pow, count($units) - 1);
228 $bytes /= pow(1024, $pow);
230 $fetchall[$base]['Filesize'] = round($bytes, $precision) . ' ' . $units[$pow];;
231 $base++;
233 return $fetchall;
237 * create a new reply for a ticket.
238 * A reply will only be added if the content isn't empty and if the ticket isn't closed.
239 * The ticket creator will be notified by email that someone else replied on his ticket.
240 * @param $content the content of the reply
241 * @param $author the author of the reply
242 * @param $ticket_id the id of the ticket to which we want to add the reply.
243 * @param $hidden boolean that specifies if the reply should only be shown to mods/admins or all users.
245 public static function createReply($content, $author, $ticket_id, $hidden){
246 //if not empty
247 if(! ( Trim ( $content ) === '' )){
248 $content = filter_var($content, FILTER_SANITIZE_STRING);
249 $ticket = new Ticket();
250 $ticket->load_With_TId($ticket_id);
251 //if status is not closed
252 if($ticket->getStatus() != 3){
253 Ticket_Reply::createReply($content, $author, $ticket_id, $hidden, $ticket->getAuthor());
255 //notify ticket author that a new reply is added!
256 if($ticket->getAuthor() != $author){
257 Mail_Handler::send_ticketing_mail($ticket->getAuthor(), $ticket, $content, "REPLY", $ticket->getForwardedGroupId());
261 }else{
262 //TODO: Show error message that ticket is closed
264 }else{
265 //TODO: Show error content is empty
271 * assign a ticket to a user.
272 * Checks if the ticket exists, if so then it will try to assign the user to it, a log entry will be written about this.
273 * @param $user_id the id of user trying to be assigned to the ticket.
274 * @param $ticket_id the id of the ticket that we try to assign to the user.
275 * @return SUCCESS_ASSIGNED, TICKET_NOT_EXISTING or ALREADY_ASSIGNED
277 public static function assignTicket($user_id, $ticket_id){
278 if(self::ticketExists($ticket_id)){
279 $returnvalue = Assigned::assignTicket($user_id, $ticket_id);
280 Ticket_Log::createLogEntry( $ticket_id, $user_id, 7);
281 return $returnvalue;
282 }else{
283 return "TICKET_NOT_EXISTING";
289 * unassign a ticket of a user.
290 * Checks if the ticket exists, if so then it will try to unassign the user of it, a log entry will be written about this.
291 * @param $user_id the id of user trying to be assigned to the ticket.
292 * @param $ticket_id the id of the ticket that we try to assign to the user.
293 * @return SUCCESS_UNASSIGNED, TICKET_NOT_EXISTING or NOT_ASSIGNED
295 public static function unAssignTicket($user_id, $ticket_id){
296 if(self::ticketExists($ticket_id)){
297 $returnvalue = Assigned::unAssignTicket($user_id, $ticket_id);
298 Ticket_Log::createLogEntry( $ticket_id, $user_id, 9);
299 return $returnvalue;
300 }else{
301 return "TICKET_NOT_EXISTING";
307 * forward a ticket to a specific support group.
308 * Checks if the ticket exists, if so then it will try to forward the ticket to the support group specified, a log entry will be written about this.
309 * if no log entry should be written then the user_id should be 0, else te $user_id will be used in the log to specify who forwarded it.
310 * @param $user_id the id of user trying to forward the ticket.
311 * @param $ticket_id the id of the ticket that we try to forward to a support group.
312 * @param $group_id the id of the support group.
313 * @return SUCCESS_FORWARDED, TICKET_NOT_EXISTING or INVALID_SGROUP
315 public static function forwardTicket($user_id, $ticket_id, $group_id){
316 if(self::ticketExists($ticket_id)){
317 if(isset($group_id) && $group_id != ""){
318 //forward the ticket
319 $returnvalue = Forwarded::forwardTicket($group_id, $ticket_id);
321 if($user_id != 0){
322 //unassign the ticket incase the ticket is assined to yourself
323 self::unAssignTicket($user_id, $ticket_id);
324 //make a log entry of this action
325 Ticket_Log::createLogEntry( $ticket_id, $user_id, 8, $group_id);
327 return $returnvalue;
328 }else{
329 return "INVALID_SGROUP";
331 }else{
332 return "TICKET_NOT_EXISTING";
339 ////////////////////////////////////////////Methods////////////////////////////////////////////////////
342 * A constructor.
343 * Empty constructor
345 public function __construct() {
351 * sets the object's attributes.
352 * @param $values should be an array of the form array('TId' => ticket_id, 'Title' => title, 'Status'=> status, 'Timestamp' => ts, 'Queue' => queue,
353 * 'Ticket_Category' => tc, 'Author' => author, 'Priority' => priority).
355 public function set($values){
356 if(isset($values['TId'])){
357 $this->tId = $values['TId'];
359 $this->title = $values['Title'];
360 $this->status = $values['Status'];
361 $this->timestamp = $values['Timestamp'];
362 $this->queue = $values['Queue'];
363 $this->ticket_category = $values['Ticket_Category'];
364 $this->author = $values['Author'];
365 $this->priority = $values['Priority'];
370 * creates a new 'ticket' entry.
371 * this method will use the object's attributes for creating a new 'ticket' entry in the database.
373 public function create(){
374 $dbl = new DBLayer("lib");
375 $this->tId = $dbl->executeReturnId("ticket", Array('Title' => $this->title, 'Status' => $this->status, 'Queue' => $this->queue, 'Ticket_Category' => $this->ticket_category, 'Author' => $this->author, 'Priority' => $this->priority), array('Timestamp'=>'now()'));
380 * loads the object's attributes.
381 * loads the object's attributes by giving a TId (ticket id).
382 * @param $id the id of the ticket that should be loaded
384 public function load_With_TId( $id) {
385 $dbl = new DBLayer("lib");
386 $statement = $dbl->select("ticket", array('id' => $id), "TId=:id");
387 $row = $statement->fetch();
388 $this->tId = $row['TId'];
389 $this->timestamp = $row['Timestamp'];
390 $this->title = $row['Title'];
391 $this->status = $row['Status'];
392 $this->queue = $row['Queue'];
393 $this->ticket_category = $row['Ticket_Category'];
394 $this->author = $row['Author'];
395 $this->priority = $row['Priority'];
400 * update the objects attributes to the db.
402 public function update(){
403 $dbl = new DBLayer("lib");
404 $dbl->update("ticket", Array('Timestamp' => $this->timestamp, 'Title' => $this->title, 'Status' => $this->status, 'Queue' => $this->queue, 'Ticket_Category' => $this->ticket_category, 'Author' => $this->author, 'Priority' => $this->priority), "TId=$this->tId");
409 * check if a ticket has a ticket_info page or not.
410 * @return true or false
412 public function hasInfo(){
413 return Ticket_Info::TicketHasInfo($this->getTId());
417 ////////////////////////////////////////////Getters////////////////////////////////////////////////////
420 * get tId attribute of the object.
422 public function getTId(){
423 return $this->tId;
427 * get timestamp attribute of the object in the format defined in the outputTime function of the Helperclass.
429 public function getTimestamp(){
430 return Helpers::outputTime($this->timestamp);
434 * get title attribute of the object.
436 public function getTitle(){
437 return $this->title;
441 * get status attribute of the object.
443 public function getStatus(){
444 return $this->status;
448 * get status attribute of the object in the form of text (string).
450 public function getStatusText(){
451 $statusArray = Ticket::getStatusArray();
452 return $statusArray[$this->getStatus()];
456 * get category attribute of the object in the form of text (string).
458 public function getCategoryName(){
459 $category = Ticket_Category::constr_TCategoryId($this->getTicket_Category());
460 return $category->getName();
464 * get queue attribute of the object.
466 public function getQueue(){
467 return $this->queue;
471 * get ticket_category attribute of the object (int).
473 public function getTicket_Category(){
474 return $this->ticket_category;
478 * get author attribute of the object (int).
480 public function getAuthor(){
481 return $this->author;
485 * get priority attribute of the object (int).
487 public function getPriority(){
488 return $this->priority;
492 * get priority attribute of the object in the form of text (string).
494 public function getPriorityText(){
495 $priorityArray = Ticket::getPriorityArray();
496 return $priorityArray[$this->getPriority()];
500 * get the user assigned to the ticket.
501 * or return 0 in case not assigned.
503 public function getAssigned(){
504 $user_id = Assigned::getUserAssignedToTicket($this->getTId());
505 if ($user_id == ""){
506 return 0;
507 }else{
508 return $user_id;
513 * get the name of the support group to whom the ticket is forwarded
514 * or return 0 in case not forwarded.
516 public function getForwardedGroupName(){
517 $group_id = Forwarded::getSGroupOfTicket($this->getTId());
518 if ($group_id == ""){
519 return 0;
520 }else{
521 return Support_Group::getGroup($group_id)->getName();
526 * get the id of the support group to whom the ticket is forwarded
527 * or return 0 in case not forwarded.
529 public function getForwardedGroupId(){
530 $group_id = Forwarded::getSGroupOfTicket($this->getTId());
531 if ($group_id == ""){
532 return 0;
533 }else{
534 return $group_id;
537 ////////////////////////////////////////////Setters////////////////////////////////////////////////////
540 * set tId attribute of the object.
541 * @param $id integer id of the ticket
543 public function setTId($id){
544 $this->tId = $id;
548 * set timestamp attribute of the object.
549 * @param $ts timestamp of the ticket
551 public function setTimestamp($ts){
552 $this->timestamp = $ts;
556 * set title attribute of the object.
557 * @param $t title of the ticket
559 public function setTitle($t){
560 $this->title = $t;
564 * set status attribute of the object.
565 * @param $s status of the ticket(int)
567 public function setStatus($s){
568 $this->status = $s;
572 * set queue attribute of the object.
573 * @param $q queue of the ticket
575 public function setQueue($q){
576 $this->queue = $q;
580 * set ticket_category attribute of the object.
581 * @param $tc ticket_category id of the ticket(int)
583 public function setTicket_Category($tc){
584 $this->ticket_category = $tc;
588 * set author attribute of the object.
589 * @param $a author of the ticket
591 public function setAuthor($a){
592 $this->author = $a;
596 * set priority attribute of the object.
597 * @param $p priority of the ticket
599 public function setPriority($p){
600 $this->priority = $p;
604 * function that creates a ticket Attachment.
606 public static function add_Attachment($TId,$filename,$author,$tempFile){
608 global $FILE_STORAGE_PATH;
609 $length = mt_rand(20, 25);
610 $characters = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ$-_.+!*\'(),';
611 $randomString = '';
612 for ($i = 0; $i < $length; $i++) {
613 $randomString .= $characters[rand(0, strlen($characters) - 1)];
615 $targetFile = $FILE_STORAGE_PATH . $randomString . "/" . $filename;
617 if(file_exists($targetFile)) { return self::add_Attachment($TId,$filename,$author,$tempFile); }
619 $ticket = new Ticket();
620 $ticket->load_With_TId($TId);
622 //create the attachment!
623 try {
624 $dbl = new DBLayer("lib");
625 $dbl->insert("`ticket_attachments`", Array('ticket_TId' => $TId, 'Filename' => $filename, 'Filesize' => filesize($tempFile), 'Uploader' => $author, 'Path' => $randomString . "/" . $filename));
627 catch (Exception $e) {
628 return $false;
632 mkdir($FILE_STORAGE_PATH . $randomString);
633 $return = move_uploaded_file($tempFile,$targetFile);
635 if ($return == false) {
636 $dbl->delete("`ticket_attachments`", array('Path' => $randomString . "/" . $filename), "`Path` = :Path");
639 //write a log entry
640 Ticket_Log::createLogEntry( $TId, $author, 10);
642 return $return;