TeamSpeak 3 PHP Framework  1.1.23
Copyright © Planet TeamSpeak. All rights reserved.
 All Classes Namespaces Files Functions Variables Pages
Reply.php
Go to the documentation of this file.
1 <?php
2 
3 /**
4  * @file
5  * TeamSpeak 3 PHP Framework
6  *
7  * $Id: Reply.php 10/11/2013 11:35:21 scp@orilla $
8  *
9  * This program is free software: you can redistribute it and/or modify
10  * it under the terms of the GNU General Public License as published by
11  * the Free Software Foundation, either version 3 of the License, or
12  * (at your option) any later version.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program. If not, see <http://www.gnu.org/licenses/>.
21  *
22  * @package TeamSpeak3
23  * @version 1.1.23
24  * @author Sven 'ScP' Paulsen
25  * @copyright Copyright (c) 2010 by Planet TeamSpeak. All rights reserved.
26  */
27 
28 /**
29  * @class TeamSpeak3_Adapter_ServerQuery_Reply
30  * @brief Provides methods to analyze and format a ServerQuery reply.
31  */
33 {
34  /**
35  * Stores the command used to get this reply.
36  *
37  * @var TeamSpeak3_Helper_String
38  */
39  protected $cmd = null;
40 
41  /**
42  * Stores the servers reply (if available).
43  *
44  * @var TeamSpeak3_Helper_String
45  */
46  protected $rpl = null;
47 
48  /**
49  * Stores connected TeamSpeak3_Node_Host object.
50  *
51  * @var TeamSpeak3_Node_Host
52  */
53  protected $con = null;
54 
55  /**
56  * Stores an assoc array containing the error info for this reply.
57  *
58  * @var array
59  */
60  protected $err = array();
61 
62  /**
63  * Sotres an array of events that occured before or during this reply.
64  *
65  * @var array
66  */
67  protected $evt = array();
68 
69  /**
70  * Indicates whether exceptions should be thrown or not.
71  *
72  * @var boolean
73  */
74  protected $exp = TRUE;
75 
76  /**
77  * Creates a new TeamSpeak3_Adapter_ServerQuery_Reply object.
78  *
79  * @param array $rpl
80  * @param string $cmd
81  * @param boolean $exp
82  * @param TeamSpeak3_Node_Host $con
83  * @return TeamSpeak3_Adapter_ServerQuery_Reply
84  */
85  public function __construct(array $rpl, $cmd = null, TeamSpeak3_Node_Host $con = null, $exp = TRUE)
86  {
87  $this->cmd = new TeamSpeak3_Helper_String($cmd);
88  $this->con = $con;
89  $this->exp = (bool) $exp;
90 
91  $this->fetchError(array_pop($rpl));
92  $this->fetchReply($rpl);
93  }
94 
95  /**
96  * Returns the reply as an TeamSpeak3_Helper_String object.
97  *
98  * @return TeamSpeak3_Helper_String
99  */
100  public function toString()
101  {
102  return (!func_num_args()) ? $this->rpl->unescape() : $this->rpl;
103  }
104 
105  /**
106  * Returns the reply as a standard PHP array where each element represents one item.
107  *
108  * @return array
109  */
110  public function toLines()
111  {
112  if(!count($this->rpl)) return array();
113 
114  $list = $this->toString(0)->split(TeamSpeak3::SEPARATOR_LIST);
115 
116  if(!func_num_args())
117  {
118  for($i = 0; $i < count($list); $i++) $list[$i]->unescape();
119  }
120 
121  return $list;
122  }
123 
124  /**
125  * Returns the reply as a standard PHP array where each element represents one item in table format.
126  *
127  * @return array
128  */
129  public function toTable()
130  {
131  $table = array();
132 
133  foreach($this->toLines(0) as $cells)
134  {
135  $pairs = $cells->split(TeamSpeak3::SEPARATOR_CELL);
136 
137  if(!func_num_args())
138  {
139  for($i = 0; $i < count($pairs); $i++) $pairs[$i]->unescape();
140  }
141 
142  $table[] = $pairs;
143  }
144 
145  return $table;
146  }
147 
148  /**
149  * Returns a multi-dimensional array containing the reply splitted in multiple rows and columns.
150  *
151  * @return array
152  */
153  public function toArray()
154  {
155  $array = array();
156  $table = $this->toTable(1);
157 
158  for($i = 0; $i < count($table); $i++)
159  {
160  foreach($table[$i] as $pair)
161  {
162  if(!count($pair))
163  {
164  continue;
165  }
166 
167  if(!$pair->contains(TeamSpeak3::SEPARATOR_PAIR))
168  {
169  $array[$i][$pair->toString()] = null;
170  }
171  else
172  {
173  list($ident, $value) = $pair->split(TeamSpeak3::SEPARATOR_PAIR, 2);
174 
175  $array[$i][$ident->toString()] = $value->isInt() ? $value->toInt() : (!func_num_args() ? $value->unescape() : $value);
176  }
177  }
178  }
179 
180  return $array;
181  }
182 
183  /**
184  * Returns a multi-dimensional assoc array containing the reply splitted in multiple rows and columns.
185  * The identifier specified by key will be used while indexing the array.
186  *
187  * @param $key
188  * @return array
189  */
190  public function toAssocArray($ident)
191  {
192  $nodes = (func_num_args() > 1) ? $this->toArray(1) : $this->toArray();
193  $array = array();
194 
195  foreach($nodes as $node)
196  {
197  if(array_key_exists($ident, $node))
198  {
199  $array[(is_object($node[$ident])) ? $node[$ident]->toString() : $node[$ident]] = $node;
200  }
201  else
202  {
203  throw new TeamSpeak3_Adapter_ServerQuery_Exception("invalid parameter", 0x602);
204  }
205  }
206 
207  return $array;
208  }
209 
210  /**
211  * Returns an array containing the reply splitted in multiple rows and columns.
212  *
213  * @return array
214  */
215  public function toList()
216  {
217  $array = func_num_args() ? $this->toArray(1) : $this->toArray();
218 
219  if(count($array) == 1)
220  {
221  return array_shift($array);
222  }
223 
224  return $array;
225  }
226 
227  /**
228  * Returns an array containing stdClass objects.
229  *
230  * @return ArrayObject
231  */
232  public function toObjectArray()
233  {
234  $array = (func_num_args() > 1) ? $this->toArray(1) : $this->toArray();
235 
236  for($i = 0; $i < count($array); $i++)
237  {
238  $array[$i] = (object) $array[$i];
239  }
240 
241  return $array;
242  }
243 
244  /**
245  * Returns the command used to get this reply.
246  *
247  * @return TeamSpeak3_Helper_String
248  */
249  public function getCommandString()
250  {
251  return new TeamSpeak3_Helper_String($this->cmd);
252  }
253 
254  /**
255  * Returns an array of events that occured before or during this reply.
256  *
257  * @return array
258  */
259  public function getNotifyEvents()
260  {
261  return $this->evt;
262  }
263 
264  /**
265  * Returns the value for a specified error property.
266  *
267  * @param string $ident
268  * @param mixed $default
269  * @return mixed
270  */
271  public function getErrorProperty($ident, $default = null)
272  {
273  return (array_key_exists($ident, $this->err)) ? $this->err[$ident] : $default;
274  }
275 
276  /**
277  * Parses a ServerQuery error and throws a TeamSpeak3_Adapter_ServerQuery_Exception object if
278  * there's an error.
279  *
280  * @param string $err
281  * @throws TeamSpeak3_Adapter_ServerQuery_Exception
282  * @return void
283  */
284  protected function fetchError($err)
285  {
286  $cells = $err->section(TeamSpeak3::SEPARATOR_CELL, 1, 3);
287 
288  foreach($cells->split(TeamSpeak3::SEPARATOR_CELL) as $pair)
289  {
290  list($ident, $value) = $pair->split(TeamSpeak3::SEPARATOR_PAIR);
291 
292  $this->err[$ident->toString()] = $value->isInt() ? $value->toInt() : $value->unescape();
293  }
294 
295  TeamSpeak3_Helper_Signal::getInstance()->emit("notifyError", $this);
296 
297  if($this->getErrorProperty("id", 0x00) != 0x00 && $this->exp)
298  {
299  if($permid = $this->getErrorProperty("failed_permid"))
300  {
301  if($permsid = key($this->con->request("permget permid=" . $permid, FALSE)->toAssocArray("permsid")))
302  {
303  $suffix = " (failed on " . $permsid . ")";
304  }
305  else
306  {
307  $suffix = " (failed on " . $this->cmd->section(TeamSpeak3::SEPARATOR_CELL) . " " . $permid . "/0x" . strtoupper(dechex($permid)) . ")";
308  }
309  }
310  elseif($details = $this->getErrorProperty("extra_msg"))
311  {
312  $suffix = " (" . trim($details) . ")";
313  }
314  else
315  {
316  $suffix = "";
317  }
318 
319  throw new TeamSpeak3_Adapter_ServerQuery_Exception($this->getErrorProperty("msg") . $suffix, $this->getErrorProperty("id"));
320  }
321  }
322 
323  /**
324  * Parses a ServerQuery reply and creates a TeamSpeak3_Helper_String object.
325  *
326  * @param string $rpl
327  * @return void
328  */
329  protected function fetchReply($rpl)
330  {
331  foreach($rpl as $key => $val)
332  {
333  if($val->startsWith(TeamSpeak3::GREET))
334  {
335  unset($rpl[$key]);
336  }
337  elseif($val->startsWith(TeamSpeak3::EVENT))
338  {
339  $this->evt[] = new TeamSpeak3_Adapter_ServerQuery_Event($rpl[$key], $this->con);
340  unset($rpl[$key]);
341  }
342  }
343 
344  $this->rpl = new TeamSpeak3_Helper_String(implode(TeamSpeak3::SEPARATOR_LIST, $rpl));
345  }
346 }