root/docs/usc/nautilus/usr2/prod/buoys/perl/xml/nusoap/lib/class.nusoap_base.php

Revision 113 (checked in by jcothran, 5 years ago)

example php/perl script to process nerrs cdmo web service data to Xenia database.

Line 
1 <?php
2
3 /*
4 $Id: class.nusoap_base.php,v 1.43 2005/08/04 01:27:42 snichol Exp $
5
6 NuSOAP - Web Services Toolkit for PHP
7
8 Copyright (c) 2002 NuSphere Corporation
9
10 This library is free software; you can redistribute it and/or
11 modify it under the terms of the GNU Lesser General Public
12 License as published by the Free Software Foundation; either
13 version 2.1 of the License, or (at your option) any later version.
14
15 This library is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
18 Lesser General Public License for more details.
19
20 You should have received a copy of the GNU Lesser General Public
21 License along with this library; if not, write to the Free Software
22 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
23
24 If you have any questions or comments, please email:
25
26 Dietrich Ayala
27 dietrich@ganx4.com
28 http://dietrich.ganx4.com/nusoap
29
30 NuSphere Corporation
31 http://www.nusphere.com
32
33 */
34
35 /* load classes
36
37 // necessary classes
38 require_once('class.soapclient.php');
39 require_once('class.soap_val.php');
40 require_once('class.soap_parser.php');
41 require_once('class.soap_fault.php');
42
43 // transport classes
44 require_once('class.soap_transport_http.php');
45
46 // optional add-on classes
47 require_once('class.xmlschema.php');
48 require_once('class.wsdl.php');
49
50 // server class
51 require_once('class.soap_server.php');*/
52
53 // class variable emulation
54 // cf. http://www.webkreator.com/php/techniques/php-static-class-variables.html
55 $GLOBALS['_transient']['static']['nusoap_base']->globalDebugLevel = 9;
56
57 /**
58 *
59 * nusoap_base
60 *
61 * @author   Dietrich Ayala <dietrich@ganx4.com>
62 * @version  $Id: class.nusoap_base.php,v 1.43 2005/08/04 01:27:42 snichol Exp $
63 * @access   public
64 */
65 class nusoap_base {
66     /**
67      * Identification for HTTP headers.
68      *
69      * @var string
70      * @access private
71      */
72     var $title = 'NuSOAP';
73     /**
74      * Version for HTTP headers.
75      *
76      * @var string
77      * @access private
78      */
79     var $version = '0.7.2';
80     /**
81      * CVS revision for HTTP headers.
82      *
83      * @var string
84      * @access private
85      */
86     var $revision = '$Revision: 1.43 $';
87     /**
88      * Current error string (manipulated by getError/setError)
89      *
90      * @var string
91      * @access private
92      */
93     var $error_str = '';
94     /**
95      * Current debug string (manipulated by debug/appendDebug/clearDebug/getDebug/getDebugAsXMLComment)
96      *
97      * @var string
98      * @access private
99      */
100     var $debug_str = '';
101     /**
102      * toggles automatic encoding of special characters as entities
103      * (should always be true, I think)
104      *
105      * @var boolean
106      * @access private
107      */
108     var $charencoding = true;
109     /**
110      * the debug level for this instance
111      *
112      * @var    integer
113      * @access private
114      */
115     var $debugLevel;
116
117     /**
118     * set schema version
119     *
120     * @var      string
121     * @access   public
122     */
123     var $XMLSchemaVersion = 'http://www.w3.org/2001/XMLSchema';
124     
125     /**
126     * charset encoding for outgoing messages
127     *
128     * @var      string
129     * @access   public
130     */
131     var $soap_defencoding = 'ISO-8859-1';
132     //var $soap_defencoding = 'UTF-8';
133
134     /**
135     * namespaces in an array of prefix => uri
136     *
137     * this is "seeded" by a set of constants, but it may be altered by code
138     *
139     * @var      array
140     * @access   public
141     */
142     var $namespaces = array(
143         'SOAP-ENV' => 'http://schemas.xmlsoap.org/soap/envelope/',
144         'xsd' => 'http://www.w3.org/2001/XMLSchema',
145         'xsi' => 'http://www.w3.org/2001/XMLSchema-instance',
146         'SOAP-ENC' => 'http://schemas.xmlsoap.org/soap/encoding/'
147         );
148
149     /**
150     * namespaces used in the current context, e.g. during serialization
151     *
152     * @var      array
153     * @access   private
154     */
155     var $usedNamespaces = array();
156
157     /**
158     * XML Schema types in an array of uri => (array of xml type => php type)
159     * is this legacy yet?
160     * no, this is used by the xmlschema class to verify type => namespace mappings.
161     * @var      array
162     * @access   public
163     */
164     var $typemap = array(
165     'http://www.w3.org/2001/XMLSchema' => array(
166         'string'=>'string','boolean'=>'boolean','float'=>'double','double'=>'double','decimal'=>'double',
167         'duration'=>'','dateTime'=>'string','time'=>'string','date'=>'string','gYearMonth'=>'',
168         'gYear'=>'','gMonthDay'=>'','gDay'=>'','gMonth'=>'','hexBinary'=>'string','base64Binary'=>'string',
169         // abstract "any" types
170         'anyType'=>'string','anySimpleType'=>'string',
171         // derived datatypes
172         'normalizedString'=>'string','token'=>'string','language'=>'','NMTOKEN'=>'','NMTOKENS'=>'','Name'=>'','NCName'=>'','ID'=>'',
173         'IDREF'=>'','IDREFS'=>'','ENTITY'=>'','ENTITIES'=>'','integer'=>'integer','nonPositiveInteger'=>'integer',
174         'negativeInteger'=>'integer','long'=>'integer','int'=>'integer','short'=>'integer','byte'=>'integer','nonNegativeInteger'=>'integer',
175         'unsignedLong'=>'','unsignedInt'=>'','unsignedShort'=>'','unsignedByte'=>'','positiveInteger'=>''),
176     'http://www.w3.org/2000/10/XMLSchema' => array(
177         'i4'=>'','int'=>'integer','boolean'=>'boolean','string'=>'string','double'=>'double',
178         'float'=>'double','dateTime'=>'string',
179         'timeInstant'=>'string','base64Binary'=>'string','base64'=>'string','ur-type'=>'array'),
180     'http://www.w3.org/1999/XMLSchema' => array(
181         'i4'=>'','int'=>'integer','boolean'=>'boolean','string'=>'string','double'=>'double',
182         'float'=>'double','dateTime'=>'string',
183         'timeInstant'=>'string','base64Binary'=>'string','base64'=>'string','ur-type'=>'array'),
184     'http://soapinterop.org/xsd' => array('SOAPStruct'=>'struct'),
185     'http://schemas.xmlsoap.org/soap/encoding/' => array('base64'=>'string','array'=>'array','Array'=>'array'),
186     'http://xml.apache.org/xml-soap' => array('Map')
187     );
188
189     /**
190     * XML entities to convert
191     *
192     * @var      array
193     * @access   public
194     * @deprecated
195     * @see    expandEntities
196     */
197     var $xmlEntities = array('quot' => '"','amp' => '&',
198         'lt' => '<','gt' => '>','apos' => "'");
199
200     /**
201     * constructor
202     *
203     * @access    public
204     */
205     function nusoap_base() {
206         $this->debugLevel = $GLOBALS['_transient']['static']['nusoap_base']->globalDebugLevel;
207     }
208
209     /**
210     * gets the global debug level, which applies to future instances
211     *
212     * @return    integer    Debug level 0-9, where 0 turns off
213     * @access    public
214     */
215     function getGlobalDebugLevel() {
216         return $GLOBALS['_transient']['static']['nusoap_base']->globalDebugLevel;
217     }
218
219     /**
220     * sets the global debug level, which applies to future instances
221     *
222     * @param    int    $level    Debug level 0-9, where 0 turns off
223     * @access    public
224     */
225     function setGlobalDebugLevel($level) {
226         $GLOBALS['_transient']['static']['nusoap_base']->globalDebugLevel = $level;
227     }
228
229     /**
230     * gets the debug level for this instance
231     *
232     * @return    int    Debug level 0-9, where 0 turns off
233     * @access    public
234     */
235     function getDebugLevel() {
236         return $this->debugLevel;
237     }
238
239     /**
240     * sets the debug level for this instance
241     *
242     * @param    int    $level    Debug level 0-9, where 0 turns off
243     * @access    public
244     */
245     function setDebugLevel($level) {
246         $this->debugLevel = $level;
247     }
248
249     /**
250     * adds debug data to the instance debug string with formatting
251     *
252     * @param    string $string debug data
253     * @access   private
254     */
255     function debug($string){
256         if ($this->debugLevel > 0) {
257             $this->appendDebug($this->getmicrotime().' '.get_class($this).": $string\n");
258         }
259     }
260
261     /**
262     * adds debug data to the instance debug string without formatting
263     *
264     * @param    string $string debug data
265     * @access   public
266     */
267     function appendDebug($string){
268         if ($this->debugLevel > 0) {
269             // it would be nice to use a memory stream here to use
270             // memory more efficiently
271             $this->debug_str .= $string;
272         }
273     }
274
275     /**
276     * clears the current debug data for this instance
277     *
278     * @access   public
279     */
280     function clearDebug() {
281         // it would be nice to use a memory stream here to use
282         // memory more efficiently
283         $this->debug_str = '';
284     }
285
286     /**
287     * gets the current debug data for this instance
288     *
289     * @return   debug data
290     * @access   public
291     */
292     function &getDebug() {
293         // it would be nice to use a memory stream here to use
294         // memory more efficiently
295         return $this->debug_str;
296     }
297
298     /**
299     * gets the current debug data for this instance as an XML comment
300     * this may change the contents of the debug data
301     *
302     * @return   debug data as an XML comment
303     * @access   public
304     */
305     function &getDebugAsXMLComment() {
306         // it would be nice to use a memory stream here to use
307         // memory more efficiently
308         while (strpos($this->debug_str, '--')) {
309             $this->debug_str = str_replace('--', '- -', $this->debug_str);
310         }
311         return "<!--\n" . $this->debug_str . "\n-->";
312     }
313
314     /**
315     * expands entities, e.g. changes '<' to '&lt;'.
316     *
317     * @param    string    $val    The string in which to expand entities.
318     * @access    private
319     */
320     function expandEntities($val) {
321         if ($this->charencoding) {
322             $val = str_replace('&', '&amp;', $val);
323             $val = str_replace("'", '&apos;', $val);
324             $val = str_replace('"', '&quot;', $val);
325             $val = str_replace('<', '&lt;', $val);
326             $val = str_replace('>', '&gt;', $val);
327         }
328         return $val;
329     }
330
331     /**
332     * returns error string if present
333     *
334     * @return   mixed error string or false
335     * @access   public
336     */
337     function getError(){
338         if($this->error_str != ''){
339             return $this->error_str;
340         }
341         return false;
342     }
343
344     /**
345     * sets error string
346     *
347     * @return   boolean $string error string
348     * @access   private
349     */
350     function setError($str){
351         $this->error_str = $str;
352     }
353
354     /**
355     * detect if array is a simple array or a struct (associative array)
356     *
357     * @param    mixed    $val    The PHP array
358     * @return    string    (arraySimple|arrayStruct)
359     * @access    private
360     */
361     function isArraySimpleOrStruct($val) {
362         $keyList = array_keys($val);
363         foreach ($keyList as $keyListValue) {
364             if (!is_int($keyListValue)) {
365                 return 'arrayStruct';
366             }
367         }
368         return 'arraySimple';
369     }
370
371     /**
372     * serializes PHP values in accordance w/ section 5. Type information is
373     * not serialized if $use == 'literal'.
374     *
375     * @param    mixed    $val    The value to serialize
376     * @param    string    $name    The name (local part) of the XML element
377     * @param    string    $type    The XML schema type (local part) for the element
378     * @param    string    $name_ns    The namespace for the name of the XML element
379     * @param    string    $type_ns    The namespace for the type of the element
380     * @param    array    $attributes    The attributes to serialize as name=>value pairs
381     * @param    string    $use    The WSDL "use" (encoded|literal)
382     * @return    string    The serialized element, possibly with child elements
383     * @access    public
384     */
385     function serialize_val($val,$name=false,$type=false,$name_ns=false,$type_ns=false,$attributes=false,$use='encoded'){
386         $this->debug("in serialize_val: name=$name, type=$type, name_ns=$name_ns, type_ns=$type_ns, use=$use");
387         $this->appendDebug('value=' . $this->varDump($val));
388         $this->appendDebug('attributes=' . $this->varDump($attributes));
389         
390         if(is_object($val) && get_class($val) == 'soapval'){
391             return $val->serialize($use);
392         }
393         // force valid name if necessary
394         if (is_numeric($name)) {
395             $name = '__numeric_' . $name;
396         } elseif (! $name) {
397             $name = 'noname';
398         }
399         // if name has ns, add ns prefix to name
400         $xmlns = '';
401         if($name_ns){
402             $prefix = 'nu'.rand(1000,9999);
403             $name = $prefix.':'.$name;
404             $xmlns .= " xmlns:$prefix=\"$name_ns\"";
405         }
406         // if type is prefixed, create type prefix
407         if($type_ns != '' && $type_ns == $this->namespaces['xsd']){
408             // need to fix this. shouldn't default to xsd if no ns specified
409             // w/o checking against typemap
410             $type_prefix = 'xsd';
411         } elseif($type_ns){
412             $type_prefix = 'ns'.rand(1000,9999);
413             $xmlns .= " xmlns:$type_prefix=\"$type_ns\"";
414         }
415         // serialize attributes if present
416         $atts = '';
417         if($attributes){
418             foreach($attributes as $k => $v){
419                 $atts .= " $k=\"".$this->expandEntities($v).'"';
420             }
421         }
422         // serialize null value
423         if (is_null($val)) {
424             if ($use == 'literal') {
425                 // TODO: depends on minOccurs
426                 return "<$name$xmlns $atts/>";
427             } else {
428                 if (isset($type) && isset($type_prefix)) {
429                     $type_str = " xsi:type=\"$type_prefix:$type\"";
430                 } else {
431                     $type_str = '';
432                 }
433                 return "<$name$xmlns$type_str $atts xsi:nil=\"true\"/>";
434             }
435         }
436         // serialize if an xsd built-in primitive type
437         if($type != '' && isset($this->typemap[$this->XMLSchemaVersion][$type])){
438             if (is_bool($val)) {
439                 if ($type == 'boolean') {
440                     $val = $val ? 'true' : 'false';
441                 } elseif (! $val) {
442                     $val = 0;
443                 }
444             } else if (is_string($val)) {
445                 $val = $this->expandEntities($val);
446             }
447             if ($use == 'literal') {
448                 return "<$name$xmlns $atts>$val</$name>";
449             } else {
450                 return "<$name$xmlns $atts xsi:type=\"xsd:$type\">$val</$name>";
451             }
452         }
453         // detect type and serialize
454         $xml = '';
455         switch(true) {
456             case (is_bool($val) || $type == 'boolean'):
457                 if ($type == 'boolean') {
458                     $val = $val ? 'true' : 'false';
459                 } elseif (! $val) {
460                     $val = 0;
461                 }
462                 if ($use == 'literal') {
463                     $xml .= "<$name$xmlns $atts>$val</$name>";
464                 } else {
465                     $xml .= "<$name$xmlns xsi:type=\"xsd:boolean\"$atts>$val</$name>";
466                 }
467                 break;
468             case (is_int($val) || is_long($val) || $type == 'int'):
469                 if ($use == 'literal') {
470                     $xml .= "<$name$xmlns $atts>$val</$name>";
471                 } else {
472                     $xml .= "<$name$xmlns xsi:type=\"xsd:int\"$atts>$val</$name>";
473                 }
474                 break;
475             case (is_float($val)|| is_double($val) || $type == 'float'):
476                 if ($use == 'literal') {
477                     $xml .= "<$name$xmlns $atts>$val</$name>";
478                 } else {
479                     $xml .= "<$name$xmlns xsi:type=\"xsd:float\"$atts>$val</$name>";
480                 }
481                 break;
482             case (is_string($val) || $type == 'string'):
483                 $val = $this->expandEntities($val);
484                 if ($use == 'literal') {
485                     $xml .= "<$name$xmlns $atts>$val</$name>";
486                 } else {
487                     $xml .= "<$name$xmlns xsi:type=\"xsd:string\"$atts>$val</$name>";
488                 }
489                 break;
490             case is_object($val):
491                 if (! $name) {
492                     $name = get_class($val);
493                     $this->debug("In serialize_val, used class name $name as element name");
494                 } else {
495                     $this->debug("In serialize_val, do not override name $name for element name for class " . get_class($val));
496                 }
497                 foreach(get_object_vars($val) as $k => $v){
498                     $pXml = isset($pXml) ? $pXml.$this->serialize_val($v,$k,false,false,false,false,$use) : $this->serialize_val($v,$k,false,false,false,false,$use);
499                 }
500                 $xml .= '<'.$name.'>'.$pXml.'</'.$name.'>';
501                 break;
502             break;
503             case (is_array($val) || $type):
504                 // detect if struct or array
505                 $valueType = $this->isArraySimpleOrStruct($val);
506                 if($valueType=='arraySimple' || ereg('^ArrayOf',$type)){
507                     $i = 0;
508                     if(is_array($val) && count($val)> 0){
509                         foreach($val as $v){
510                             if(is_object($v) && get_class($v) ==  'soapval'){
511                                 $tt_ns = $v->type_ns;
512                                 $tt = $v->type;
513                             } elseif (is_array($v)) {
514                                 $tt = $this->isArraySimpleOrStruct($v);
515                             } else {
516                                 $tt = gettype($v);
517                             }
518                             $array_types[$tt] = 1;
519                             // TODO: for literal, the name should be $name
520                             $xml .= $this->serialize_val($v,'item',false,false,false,false,$use);
521                             ++$i;
522                         }
523                         if(count($array_types) > 1){
524                             $array_typename = 'xsd:anyType';
525                         } elseif(isset($tt) && isset($this->typemap[$this->XMLSchemaVersion][$tt])) {
526                             if ($tt == 'integer') {
527                                 $tt = 'int';
528                             }
529                             $array_typename = 'xsd:'.$tt;
530                         } elseif(isset($tt) && $tt == 'arraySimple'){
531                             $array_typename = 'SOAP-ENC:Array';
532                         } elseif(isset($tt) && $tt == 'arrayStruct'){
533                             $array_typename = 'unnamed_struct_use_soapval';
534                         } else {
535                             // if type is prefixed, create type prefix
536                             if ($tt_ns != '' && $tt_ns == $this->namespaces['xsd']){
537                                  $array_typename = 'xsd:' . $tt;
538                             } elseif ($tt_ns) {
539                                 $tt_prefix = 'ns' . rand(1000, 9999);
540                                 $array_typename = "$tt_prefix:$tt";
541                                 $xmlns .= " xmlns:$tt_prefix=\"$tt_ns\"";
542                             } else {
543                                 $array_typename = $tt;
544                             }
545                         }
546                         $array_type = $i;
547                         if ($use == 'literal') {
548                             $type_str = '';
549                         } else if (isset($type) && isset($type_prefix)) {
550                             $type_str = " xsi:type=\"$type_prefix:$type\"";
551                         } else {
552                             $type_str = " xsi:type=\"SOAP-ENC:Array\" SOAP-ENC:arrayType=\"".$array_typename."[$array_type]\"";
553                         }
554                     // empty array
555                     } else {
556                         if ($use == 'literal') {
557                             $type_str = '';
558                         } else if (isset($type) && isset($type_prefix)) {
559                             $type_str = " xsi:type=\"$type_prefix:$type\"";
560                         } else {
561                             $type_str = " xsi:type=\"SOAP-ENC:Array\" SOAP-ENC:arrayType=\"xsd:anyType[0]\"";
562                         }
563                     }
564                     // TODO: for array in literal, there is no wrapper here
565                     $xml = "<$name$xmlns$type_str$atts>".$xml."</$name>";
566                 } else {
567                     // got a struct
568                     if(isset($type) && isset($type_prefix)){
569                         $type_str = " xsi:type=\"$type_prefix:$type\"";
570                     } else {
571                         $type_str = '';
572                     }
573                     if ($use == 'literal') {
574                         $xml .= "<$name$xmlns $atts>";
575                     } else {
576                         $xml .= "<$name$xmlns$type_str$atts>";
577                     }
578                     foreach($val as $k => $v){
579                         // Apache Map
580                         if ($type == 'Map' && $type_ns == 'http://xml.apache.org/xml-soap') {
581                             $xml .= '<item>';
582                             $xml .= $this->serialize_val($k,'key',false,false,false,false,$use);
583                             $xml .= $this->serialize_val($v,'value',false,false,false,false,$use);
584                             $xml .= '</item>';
585                         } else {
586                             $xml .= $this->serialize_val($v,$k,false,false,false,false,$use);
587                         }
588                     }
589                     $xml .= "</$name>";
590                 }
591                 break;
592             default:
593                 $xml .= 'not detected, got '.gettype($val).' for '.$val;
594                 break;
595         }
596         return $xml;
597     }
598
599     /**
600     * serializes a message
601     *
602     * @param string $body the XML of the SOAP body
603     * @param mixed $headers optional string of XML with SOAP header content, or array of soapval objects for SOAP headers
604     * @param array $namespaces optional the namespaces used in generating the body and headers
605     * @param string $style optional (rpc|document)
606     * @param string $use optional (encoded|literal)
607     * @param string $encodingStyle optional (usually 'http://schemas.xmlsoap.org/soap/encoding/' for encoded)
608     * @return string the message
609     * @access public
610     */
611     function serializeEnvelope($body,$headers=false,$namespaces=array(),$style='rpc',$use='encoded',$encodingStyle='http://schemas.xmlsoap.org/soap/encoding/'){
612     // TODO: add an option to automatically run utf8_encode on $body and $headers
613     // if $this->soap_defencoding is UTF-8.  Not doing this automatically allows
614     // one to send arbitrary UTF-8 characters, not just characters that map to ISO-8859-1
615
616     $this->debug("In serializeEnvelope length=" . strlen($body) . " body (max 1000 characters)=" . substr($body, 0, 1000) . " style=$style use=$use encodingStyle=$encodingStyle");
617     $this->debug("headers:");
618     $this->appendDebug($this->varDump($headers));
619     $this->debug("namespaces:");
620     $this->appendDebug($this->varDump($namespaces));
621
622     // serialize namespaces
623     $ns_string = '';
624     foreach(array_merge($this->namespaces,$namespaces) as $k => $v){
625         $ns_string .= " xmlns:$k=\"$v\"";
626     }
627     if($encodingStyle) {
628         $ns_string = " SOAP-ENV:encodingStyle=\"$encodingStyle\"$ns_string";
629     }
630
631     // serialize headers
632     if($headers){
633         if (is_array($headers)) {
634             $xml = '';
635             foreach ($headers as $header) {
636                 $xml .= $this->serialize_val($header, false, false, false, false, false, $use);
637             }
638             $headers = $xml;
639             $this->debug("In serializeEnvelope, serialzied array of headers to $headers");
640         }
641         $headers = "<SOAP-ENV:Header>".$headers."</SOAP-ENV:Header>";
642     }
643     // serialize envelope
644     return
645     '<?xml version="1.0" encoding="'.$this->soap_defencoding .'"?'.">".
646     '<SOAP-ENV:Envelope'.$ns_string.">".
647     $headers.
648     "<SOAP-ENV:Body>".
649         $body.
650     "</SOAP-ENV:Body>".
651     "</SOAP-ENV:Envelope>";
652     }
653
654     /**
655      * formats a string to be inserted into an HTML stream
656      *
657      * @param string $str The string to format
658      * @return string The formatted string
659      * @access public
660      * @deprecated
661      */
662     function formatDump($str){
663         $str = htmlspecialchars($str);
664         return nl2br($str);
665     }
666
667     /**
668     * contracts (changes namespace to prefix) a qualified name
669     *
670     * @param    string $qname qname
671     * @return    string contracted qname
672     * @access   private
673     */
674     function contractQname($qname){
675         // get element namespace
676         //$this->xdebug("Contract $qname");
677         if (strrpos($qname, ':')) {
678             // get unqualified name
679             $name = substr($qname, strrpos($qname, ':') + 1);
680             // get ns
681             $ns = substr($qname, 0, strrpos($qname, ':'));
682             $p = $this->getPrefixFromNamespace($ns);
683             if ($p) {
684                 return $p . ':' . $name;
685             }
686             return $qname;
687         } else {
688             return $qname;
689         }
690     }
691
692     /**
693     * expands (changes prefix to namespace) a qualified name
694     *
695     * @param    string $string qname
696     * @return    string expanded qname
697     * @access   private
698     */
699     function expandQname($qname){
700         // get element prefix
701         if(strpos($qname,':') && !ereg('^http://',$qname)){
702             // get unqualified name
703             $name = substr(strstr($qname,':'),1);
704             // get ns prefix
705             $prefix = substr($qname,0,strpos($qname,':'));
706             if(isset($this->namespaces[$prefix])){
707                 return $this->namespaces[$prefix].':'.$name;
708             } else {
709                 return $qname;
710             }
711         } else {
712             return $qname;
713         }
714     }
715
716     /**
717     * returns the local part of a prefixed string
718     * returns the original string, if not prefixed
719     *
720     * @param string $str The prefixed string
721     * @return string The local part
722     * @access public
723     */
724     function getLocalPart($str){
725         if($sstr = strrchr($str,':')){
726             // get unqualified name
727             return substr( $sstr, 1 );
728         } else {
729             return $str;
730         }
731     }
732
733     /**
734     * returns the prefix part of a prefixed string
735     * returns false, if not prefixed
736     *
737     * @param string $str The prefixed string
738     * @return mixed The prefix or false if there is no prefix
739     * @access public
740     */
741     function getPrefix($str){
742         if($pos = strrpos($str,':')){
743             // get prefix
744             return substr($str,0,$pos);
745         }
746         return false;
747     }
748
749     /**
750     * pass it a prefix, it returns a namespace
751     *
752     * @param string $prefix The prefix
753     * @return mixed The namespace, false if no namespace has the specified prefix
754     * @access public
755     */
756     function getNamespaceFromPrefix($prefix){
757         if (isset($this->namespaces[$prefix])) {
758             return $this->namespaces[$prefix];
759         }
760         //$this->setError("No namespace registered for prefix '$prefix'");
761         return false;
762     }
763
764     /**
765     * returns the prefix for a given namespace (or prefix)
766     * or false if no prefixes registered for the given namespace
767     *
768     * @param string $ns The namespace
769     * @return mixed The prefix, false if the namespace has no prefixes
770     * @access public
771     */
772     function getPrefixFromNamespace($ns) {
773         foreach ($this->namespaces as $p => $n) {
774             if ($ns == $n || $ns == $p) {
775                 $this->usedNamespaces[$p] = $n;
776                 return $p;
777             }
778         }
779         return false;
780     }
781
782     /**
783     * returns the time in ODBC canonical form with microseconds
784     *
785     * @return string The time in ODBC canonical form with microseconds
786     * @access public
787     */
788     function getmicrotime() {
789         if (function_exists('gettimeofday')) {
790             $tod = gettimeofday();
791             $sec = $tod['sec'];
792             $usec = $tod['usec'];
793         } else {
794             $sec = time();
795             $usec = 0;
796         }
797         return strftime('%Y-%m-%d %H:%M:%S', $sec) . '.' . sprintf('%06d', $usec);
798     }
799
800     /**
801      * Returns a string with the output of var_dump
802      *
803      * @param mixed $data The variable to var_dump
804      * @return string The output of var_dump
805      * @access public
806      */
807     function varDump($data) {
808         ob_start();
809         var_dump($data);
810         $ret_val = ob_get_contents();
811         ob_end_clean();
812         return $ret_val;
813     }
814 }
815
816 // XML Schema Datatype Helper Functions
817
818 //xsd:dateTime helpers
819
820 /**
821 * convert unix timestamp to ISO 8601 compliant date string
822 *
823 * @param    string $timestamp Unix time stamp
824 * @access   public
825 */
826 function timestamp_to_iso8601($timestamp,$utc=true){
827     $datestr = date('Y-m-d\TH:i:sO',$timestamp);
828     if($utc){
829         $eregStr =
830         '([0-9]{4})-'.    // centuries & years CCYY-
831         '([0-9]{2})-'.    // months MM-
832         '([0-9]{2})'.    // days DD
833         'T'.            // separator T
834         '([0-9]{2}):'.    // hours hh:
835         '([0-9]{2}):'.    // minutes mm:
836         '([0-9]{2})(\.[0-9]*)?'. // seconds ss.ss...
837         '(Z|[+\-][0-9]{2}:?[0-9]{2})?'; // Z to indicate UTC, -/+HH:MM:SS.SS... for local tz's
838
839         if(ereg($eregStr,$datestr,$regs)){
840             return sprintf('%04d-%02d-%02dT%02d:%02d:%02dZ',$regs[1],$regs[2],$regs[3],$regs[4],$regs[5],$regs[6]);
841         }
842         return false;
843     } else {
844         return $datestr;
845     }
846 }
847
848 /**
849 * convert ISO 8601 compliant date string to unix timestamp
850 *
851 * @param    string $datestr ISO 8601 compliant date string
852 * @access   public
853 */
854 function iso8601_to_timestamp($datestr){
855     $eregStr =
856     '([0-9]{4})-'.    // centuries & years CCYY-
857     '([0-9]{2})-'.    // months MM-
858     '([0-9]{2})'.    // days DD
859     'T'.            // separator T
860     '([0-9]{2}):'.    // hours hh:
861     '([0-9]{2}):'.    // minutes mm:
862     '([0-9]{2})(\.[0-9]+)?'. // seconds ss.ss...
863     '(Z|[+\-][0-9]{2}:?[0-9]{2})?'; // Z to indicate UTC, -/+HH:MM:SS.SS... for local tz's
864     if(ereg($eregStr,$datestr,$regs)){
865         // not utc
866         if($regs[8] != 'Z'){
867             $op = substr($regs[8],0,1);
868             $h = substr($regs[8],1,2);
869             $m = substr($regs[8],strlen($regs[8])-2,2);
870             if($op == '-'){
871                 $regs[4] = $regs[4] + $h;
872                 $regs[5] = $regs[5] + $m;
873             } elseif($op == '+'){
874                 $regs[4] = $regs[4] - $h;
875                 $regs[5] = $regs[5] - $m;
876             }
877         }
878         return strtotime("$regs[1]-$regs[2]-$regs[3] $regs[4]:$regs[5]:$regs[6]Z");
879     } else {
880         return false;
881     }
882 }
883
884 /**
885 * sleeps some number of microseconds
886 *
887 * @param    string $usec the number of microseconds to sleep
888 * @access   public
889 * @deprecated
890 */
891 function usleepWindows($usec)
892 {
893     $start = gettimeofday();
894     
895     do
896     {
897         $stop = gettimeofday();
898         $timePassed = 1000000 * ($stop['sec'] - $start['sec'])
899         + $stop['usec'] - $start['usec'];
900     }
901     while ($timePassed < $usec);
902 }
903
904
905 ?>
Note: See TracBrowser for help on using the browser.