3 * base include file for SimpleTest
5 * @subpackage WebTester
6 * @version $Id: encoding.php,v 1.17 2005/07/20 13:41:40 lastcraft Exp $
10 * include other SimpleTest class files
12 require_once(dirname(__FILE__
) . '/socket.php');
16 * Single post parameter.
18 * @subpackage WebTester
20 class SimpleEncodedPair
{
25 * Stashes the data for rendering later.
26 * @param string $key Form element name.
27 * @param string $value Data to send.
29 function SimpleEncodedPair($key, $value) {
31 $this->_value
= $value;
35 * The pair as a single string.
36 * @return string Encoded pair.
39 function asRequest() {
40 return $this->_key
. '=' . urlencode($this->_value
);
44 * The MIME part as a string.
45 * @return string MIME part encoding.
49 $part = 'Content-Disposition: form-data; ';
50 $part .= "name=\"" . $this->_key
. "\"\r\n";
51 $part .= "\r\n" . $this->_value
;
56 * Is this the value we are looking for?
57 * @param string $key Identifier.
58 * @return boolean True if matched.
61 function isKey($key) {
62 return $key == $this->_key
;
66 * Is this the value we are looking for?
67 * @return string Identifier.
75 * Is this the value we are looking for?
76 * @return string Content.
85 * Single post parameter.
87 * @subpackage WebTester
89 class SimpleAttachment
{
95 * Stashes the data for rendering later.
96 * @param string $key Key to add value to.
97 * @param string $content Raw data.
98 * @param hash $filename Original filename.
100 function SimpleAttachment($key, $content, $filename) {
102 $this->_content
= $content;
103 $this->_filename
= $filename;
107 * The pair as a single string.
108 * @return string Encoded pair.
111 function asRequest() {
116 * The MIME part as a string.
117 * @return string MIME part encoding.
121 $part = 'Content-Disposition: form-data; ';
122 $part .= 'name="' . $this->_key
. '"; ';
123 $part .= 'filename="' . $this->_filename
. '"';
124 $part .= "\r\nContent-Type: " . $this->_deduceMimeType();
125 $part .= "\r\n\r\n" . $this->_content
;
130 * Attempts to figure out the MIME type from the
131 * file extension and the content.
132 * @return string MIME type.
135 function _deduceMimeType() {
136 if ($this->_isOnlyAscii($this->_content
)) {
139 return 'application/octet-stream';
143 * Tests each character is in the range 0-127.
144 * @param string $ascii String to test.
147 function _isOnlyAscii($ascii) {
148 for ($i = 0, $length = strlen($ascii); $i < $length; $i++
) {
149 if (ord($ascii[$i]) > 127) {
157 * Is this the value we are looking for?
158 * @param string $key Identifier.
159 * @return boolean True if matched.
162 function isKey($key) {
163 return $key == $this->_key
;
167 * Is this the value we are looking for?
168 * @return string Identifier.
176 * Is this the value we are looking for?
177 * @return string Content.
180 function getValue() {
181 return $this->_filename
;
186 * Bundle of GET/POST parameters. Can include
187 * repeated parameters.
188 * @package SimpleTest
189 * @subpackage WebTester
191 class SimpleEncoding
{
196 * @param array $query Hash of parameters.
197 * Multiple values are
198 * as lists on a single key.
201 function SimpleEncoding($query = false) {
206 $this->merge($query);
210 * Empties the request of parameters.
214 $this->_request
= array();
218 * Adds a parameter to the query.
219 * @param string $key Key to add value to.
220 * @param string/array $value New data.
223 function add($key, $value) {
224 if ($value === false) {
227 if (is_array($value)) {
228 foreach ($value as $item) {
229 $this->_addPair($key, $item);
232 $this->_addPair($key, $value);
237 * Adds a new value into the request.
238 * @param string $key Key to add value to.
239 * @param string/array $value New data.
242 function _addPair($key, $value) {
243 $this->_request
[] = new SimpleEncodedPair($key, $value);
247 * Adds a MIME part to the query. Does nothing for a
248 * form encoded packet.
249 * @param string $key Key to add value to.
250 * @param string $content Raw data.
251 * @param hash $filename Original filename.
254 function attach($key, $content, $filename) {
255 $this->_request
[] = new SimpleAttachment($key, $content, $filename);
259 * Adds a set of parameters to this query.
260 * @param array/SimpleQueryString $query Multiple values are
261 * as lists on a single key.
264 function merge($query) {
265 if (is_object($query)) {
266 $this->_request
= array_merge($this->_request
, $query->getAll());
267 } elseif (is_array($query)) {
268 foreach ($query as $key => $value) {
269 $this->add($key, $value);
275 * Accessor for single value.
276 * @return string/array False if missing, string
277 * if present and array if
281 function getValue($key) {
283 foreach ($this->_request
as $pair) {
284 if ($pair->isKey($key)) {
285 $values[] = $pair->getValue();
288 if (count($values) == 0) {
290 } elseif (count($values) == 1) {
298 * Accessor for listing of pairs.
299 * @return array All pair objects.
303 return $this->_request
;
307 * Renders the query string as a URL encoded
309 * @return string Part of URL.
313 $statements = array();
314 foreach ($this->_request
as $pair) {
315 if ($statement = $pair->asRequest()) {
316 $statements[] = $statement;
319 return implode('&', $statements);
324 * Bundle of GET parameters. Can include
325 * repeated parameters.
326 * @package SimpleTest
327 * @subpackage WebTester
329 class SimpleGetEncoding
extends SimpleEncoding
{
333 * @param array $query Hash of parameters.
334 * Multiple values are
335 * as lists on a single key.
338 function SimpleGetEncoding($query = false) {
339 $this->SimpleEncoding($query);
343 * HTTP request method.
344 * @return string Always GET.
347 function getMethod() {
352 * Writes no extra headers.
353 * @param SimpleSocket $socket Socket to write to.
356 function writeHeadersTo(&$socket) {
360 * No data is sent to the socket as the data is encoded into
362 * @param SimpleSocket $socket Socket to write to.
365 function writeTo(&$socket) {
369 * Renders the query string as a URL encoded
370 * request part for attaching to a URL.
371 * @return string Part of URL.
374 function asUrlRequest() {
375 return $this->_encode();
380 * Bundle of URL parameters for a HEAD request.
381 * @package SimpleTest
382 * @subpackage WebTester
384 class SimpleHeadEncoding
extends SimpleGetEncoding
{
388 * @param array $query Hash of parameters.
389 * Multiple values are
390 * as lists on a single key.
393 function SimpleHeadEncoding($query = false) {
394 $this->SimpleGetEncoding($query);
398 * HTTP request method.
399 * @return string Always HEAD.
402 function getMethod() {
408 * Bundle of POST parameters. Can include
409 * repeated parameters.
410 * @package SimpleTest
411 * @subpackage WebTester
413 class SimplePostEncoding
extends SimpleEncoding
{
417 * @param array $query Hash of parameters.
418 * Multiple values are
419 * as lists on a single key.
422 function SimplePostEncoding($query = false) {
423 $this->SimpleEncoding($query);
427 * HTTP request method.
428 * @return string Always POST.
431 function getMethod() {
436 * Dispatches the form headers down the socket.
437 * @param SimpleSocket $socket Socket to write to.
440 function writeHeadersTo(&$socket) {
441 $socket->write("Content-Length: " . (integer)strlen($this->_encode()) . "\r\n");
442 $socket->write("Content-Type: application/x-www-form-urlencoded\r\n");
446 * Dispatches the form data down the socket.
447 * @param SimpleSocket $socket Socket to write to.
450 function writeTo(&$socket) {
451 $socket->write($this->_encode());
455 * Renders the query string as a URL encoded
456 * request part for attaching to a URL.
457 * @return string Part of URL.
460 function asUrlRequest() {
466 * Bundle of POST parameters in the multipart
467 * format. Can include file uploads.
468 * @package SimpleTest
469 * @subpackage WebTester
471 class SimpleMultipartEncoding
extends SimplePostEncoding
{
476 * @param array $query Hash of parameters.
477 * Multiple values are
478 * as lists on a single key.
481 function SimpleMultipartEncoding($query = false, $boundary = false) {
482 $this->SimplePostEncoding($query);
483 $this->_boundary
= ($boundary === false ?
uniqid('st') : $boundary);
487 * Dispatches the form headers down the socket.
488 * @param SimpleSocket $socket Socket to write to.
491 function writeHeadersTo(&$socket) {
492 $socket->write("Content-Length: " . (integer)strlen($this->_encode()) . "\r\n");
493 $socket->write("Content-Type: multipart/form-data, boundary=" . $this->_boundary
. "\r\n");
497 * Dispatches the form data down the socket.
498 * @param SimpleSocket $socket Socket to write to.
501 function writeTo(&$socket) {
502 $socket->write($this->_encode());
506 * Renders the query string as a URL encoded
508 * @return string Part of URL.
513 foreach ($this->_request
as $pair) {
514 $stream .= "--" . $this->_boundary
. "\r\n";
515 $stream .= $pair->asMime() . "\r\n";
517 $stream .= "--" . $this->_boundary
. "--\r\n";