Xataface 2.0
Xataface Application Framework
Dataface/XMLTool.php
Go to the documentation of this file.
00001 <?php
00002 class Dataface_XMLTool {
00003 
00004         var $ns="df";
00005         var $perms_ns = "dfp";
00006         var $atts_ns = "dfa";
00007         var $http_ns = "http";
00008         
00009         var $required_tables_loaded = array();
00010         
00016         var $ifModifiedSince=array();
00017         
00018         
00019         public static function &getOutputCache(){
00020                 static $cache =0;
00021                 if ( !is_object($cache) ){
00022                         import('Dataface/OutputCache.php');
00023                         $cache = new Dataface_OutputCache();
00024                 }
00025                 return $cache;
00026         }
00027         
00028         
00029         function setIfModifiedSince($type, $name, $timestamp){
00030                 $this->ifModifiedSince[$type][$name] = $timestamp;
00031         }
00032         
00033         function getIfModifiedSince($type, $name){
00034                 if ( isset($this->ifModifiedSince[$type][$name]) ) {
00035                         return $this->ifModifiedSince[$type][$name];
00036                 } else {
00037                         return null;
00038                 }
00039         }
00040         
00041         function isModified($type, $name, $timestamp){
00042                 $since = $this->getIfModifiedSince($type, $name);
00043                 if ( $since < $timestamp ){
00044                         return true;
00045                 } else {
00046                         return false;
00047                 }
00048         }
00049         
00055         function tableIsModified($name){
00056                 $cache =& $this->getOutputCache();
00057                 $time = $this->getIfModifiedSince('tables',$name);
00058                 if ( $time == null ) return true;
00059                 
00060                 return $cache->isModified($time, $name);
00061         }
00062         
00063         function valuelistIsModified($table, $name){
00064                 
00065         }
00066         
00067         
00068         function toXML(&$arg){
00069                 $class = get_class($arg);
00070                 if ( is_array($arg) ){
00071                         return toXML_array($arg);
00072                 }
00073                 eval('$result = $this->toXML_'.$class.'($arg);');
00074                 return $result;
00075         }
00076         
00077         function toXML_array($arg){
00078                 trigger_error("Not implemented yet.", E_USER_ERROR);
00079         
00080 
00081         }
00082 
00083         function markRequiredTableLoaded($name){
00084         
00085                 $this->required_tables_loaded[$name] = true;
00086         }
00087         
00088         function addRequiredTable($name){
00089                 if ( !isset($this->required_tables_loaded[$name]) ) $this->required_tables_loaded[$name] = false;
00090         }
00091         
00092         function requiredTablesToXML(){
00093                 $out = array();
00094                 foreach ( $this->required_tables_loaded as $tablename=>$loaded){
00095                         if (!$loaded){
00096                                 $t =& Dataface_Table::loadTable($tablename);
00097                                 $out[] = $this->toXML($t);
00098                                 unset($t);
00099                         }
00100                 }
00101                 return implode("\n", $out);
00102         }
00103         
00104         function toXML_Dataface_Table(&$table){
00105                 
00106                 $ns = $this->ns;
00107                 $pns = $this->perms_ns;
00108                 $ans = $this->atts_ns;
00109                 list($tablename, $tablelabel) = array_map(array(&$this,'xmlentities'), array($table->tablename, $table->getLabel()));
00110                 $out = array();
00111                 
00112                 if ( !$this->tableIsModified($table->tablename) ){
00113                         $out[] = "<$ns:table id=\"tables.{$tablename}\" name=\"$tablename\" http:status-code=\"304\" http:status-message=\"Not Modified\"></$ns:table>";
00114                         
00115                 } else {
00116                         
00117                         $out[] = <<<END
00118 <$ns:table id="tables.{$tablename}" name="$tablename" label="$tablelabel">
00119 END;
00120                         $perms = $table->getPermissions();
00121                         $patts = array();
00122                         foreach ($perms as $pname=>$pval){
00123                                 $pname = str_replace(' ', '_', $pname);
00124                                 $patts[] = $pns.':'.$pname.'="'.$pval.'"';
00125                         }
00126                         $patts = implode(' ',$patts);
00127                         $out[] = "\t<$ns:permissions $patts/>";
00128                         foreach ( $table->fields() as $field ){
00129                                 $atts = array();
00130                                 foreach ($field as $key=>$val){
00131                                         if ( is_scalar($val) ){
00132                                                 $atts[] = $ans.':'.$key.'="'.$this->xmlentities($val).'"';
00133                                         }
00134                                 }
00135                                 $atts = implode(' ', $atts);
00136                                 $out[] = "\t<$ns:field id=\"tables.{$tablename}.fields.{$field['name']}\" $atts>";
00137                                 
00138                                 $fperms = $table->getPermissions(array('field'=>$field['name']));
00139                                 $fpatts = array();
00140                                 foreach ($fperms as $fpkey=>$fpval){
00141                                         $fpkey = str_replace(' ', '_', $fpkey);
00142                                         $fpatts[] = $ans.':'.$fpkey.'="'.$fpval.'"';
00143                                 }
00144                                 $fpatts = implode(' ',$fpatts);
00145                                 $out[] = "\t\t<$ns:permissions $fpatts/>";
00146                                 
00147                                 $widget = $field['widget'];
00148                                 $watts = array();
00149                                 foreach ($widget as $wkey=>$wval){
00150                                         
00151                                         if ( is_scalar($wval) ){
00152                                                 $watts[] = $ans.':'.$wkey.'="'.$this->xmlentities($wval).'"';
00153                                         }
00154                                         
00155                                 }
00156                                 $watts = implode(' ',$watts);
00157                                 $out[] = "\t\t<$ns:widget $watts>";
00158                                 if ( isset($widget['atts']) ){
00159                                         $aatts = array();
00160                                         foreach ($widget['atts'] as $akey=>$aval){
00161                                                 if (is_scalar($aval) ){
00162                                                         $aatts[] = $ans.':'.$akey.'="'.$this->xmlentities($aval).'"';
00163                                                 }
00164                                                 
00165                                                 
00166                                         }
00167                                         $aatts = implode(' ',$aatts);
00168                                         $out[] = "\t\t\t<$ns:html_atts $aatts />";
00169                                 }
00170                                 $out[] = "\t\t</$ns:widget>";
00171                                 $out[] = "\t</$ns:field>";
00172                                         
00173                         }
00174                         
00175                         foreach ($table->relationships() as $relationship){
00176                                 $out[] = $this->toXML_Dataface_Relationship($relationship);
00177                         }
00178                         $out[] = "</$ns:table>";
00179                 }
00180                 $this->markRequiredTableLoaded($table->tablename);
00181                 return implode("\n", $out);
00182         }
00183         
00184         
00185         function toXML_Dataface_Relationship(&$relationship){
00186                 $ns = $this->ns;
00187                 $ans = $this->atts_ns;
00188                 $out = array();
00189                 $atts = array();
00190                 $name = $this->xmlentities($relationship->getName());
00191                 foreach ($relationship->_schema as $key=>$val){
00192                         if ( is_scalar($val) ){
00193                                 $atts[] = $ans.':'.$key.'="'.$this->xmlentities($val).'"';
00194                         }
00195                 }
00196                 $sourceTable =& $relationship->getSourceTable();
00197                 $tablename = $sourceTable->tablename;
00198                 $atts = implode(' ',$atts);
00199                 $out[] = "\t<$ns:relationship id=\"tables.{$tablename}.relationships.{$name}\" name=\"$name\" $atts />";
00200                 return implode("\n", $out);
00201         }
00202         
00203         function toXML_Dataface_Record(&$record){
00204         
00205                 $ns = $this->ns;
00206                 $ans = $this->atts_ns;
00207                 $pns = $this->perms_ns;
00208                 
00209                 $out = array();
00210                 $out[] = "\t\t<$ns:record id=\"".$this->xmlentities($record->getId())."\" table=\"".$record->_table->tablename."\">";
00211                 
00212                 $perms = $record->getPermissions();
00213                 $patts = array();
00214                 foreach ($perms as $pkey=>$pval){
00215                         $pkey = str_replace(' ', '_', $pkey);
00216                         $patts[] = "$pns:$pkey=\"".$this->xmlentities($pval)."\"";
00217                 }
00218                 $patts = implode(' ', $patts);
00219                 $out[] = "\t\t\t<$ns:permissions $patts/>";
00220                 
00221                 foreach ( $record->_table->fields() as $field){
00222                         $value = $record->val($field['name']);
00223                         $dispVal = $record->display($field['name']);
00224                         $this->addRequiredTable($field['table']);
00225                                 // Make sure that the table definition for this field is loaded.
00226                         $out[] = "\t\t\t<$ns:record_value field=\"".$this->xmlentities($field['name'])."\">";
00227                         $perms = $record->getPermissions(array('field'=>$field['name']));
00228                         $patts = array();
00229                         foreach ($perms as $pkey=>$pval){
00230                                 $pkey = str_replace(' ', '_', $pkey);
00231                                 $patts[] = "$pns:$pkey=\"".$this->xmlentities($pval)."\"";
00232                         }
00233                         $patts = implode(' ', $patts);
00234                         $out[] = "\t\t\t\t<$ns:permissions $patts/>";
00235                         if ( $record->_table->isDate($field['name']) ){
00236                                 $value= $dispVal;
00237                         }
00238                         
00239                         if ( @$field['vocabulary'] ) $valuelist =& $record->_table->getValuelist($field['vocabulary']);
00240                         
00241                         if ( !is_array($value)  ) $value = array($value);
00242 
00243                         foreach ($value as $vkey=>$vval){
00244                                 // $vkey will be the value that is actually stored in the database.
00245                                 // $vval Will be the resulting value after joins and valuelists are factored in.
00246                                 // We output both to save from having to publish the entire valuelist to the client.
00247                                 $vkey=$vval;    // Only fields that use vocabularies should have different key than value.
00248                                 if ( isset($valuelist) and isset($valuelist[$vval]) ){
00249 
00250                                         $vval = $valuelist[$vval];
00251                                 } 
00252                                 $out[] = "\t\t\t\t<$ns:value key=\"".$this->xmlentities($vkey)."\">".$this->xmlentities($vval)."</$ns:value>";
00253                         }
00254                         unset($valuelist);
00255                         
00256                         $out[] = "\t\t\t\t<$ns:display_value>".$this->xmlentities($dispVal)."</$ns:display_value>";
00257                         $out[] = "\t\t\t\t<$ns:html_value>".$this->xmlentities( $record->htmlValue($field['name']))."</$ns:html_value>";
00258                         $out[] = "\t\t\t</$ns:record_value>";
00259                         
00260                 
00261                 }
00262                 
00263                 $out[] = "\t\t</$ns:record>";
00264                 $out = implode("\n", $out);
00265                 return $out;
00266                 
00267                 
00268         }
00269         
00270         function toXML_Dataface_QueryTool(&$tool){
00271                 $ns = $this->ns;
00272                 $ans = $this->atts_ns;
00273                 $out = array();
00274                 $tablename = $tool->_tablename;
00275                 $tool->loadSet();
00276                 
00277                 
00278                 
00279                 $out[] = "<$ns:results source=\"".$this->xmlentities($tablename)."\" start=\"".$this->xmlentities($tool->start())."\" end=\"".$this->xmlentities($tool->end())."\" limit=\"".$this->xmlentities($tool->limit())."\" cursor=\"".$this->xmlentities($tool->cursor())."\" cardinality=\"".$this->xmlentities($tool->cardinality())."\" found=\"".$this->xmlentities($tool->found())."\" >";
00280                 $table =& Dataface_Table::loadTable($tablename);
00281                 foreach ($table->fields() as $field){
00282                         if ( Dataface_PermissionsTool::checkPermission('view', $table, array('field'=>$field['name']))){
00283                                 $this->addRequiredTable($tablename);
00284                                 $out[] = "\t<$ns:column table=\"".$this->xmlentities($tablename)."\">".$this->xmlentities($field['name'])."</$ns:column>";
00285                         }
00286                 }
00287                 
00288                 $it =& $tool->iterator();
00289                 while ($it->hasNext()){
00290                         $nex =& $it->next();
00291                         $out[] = $this->toXML_Dataface_Record($nex);
00292                         unset($nex);
00293                 }
00294                 $out[] = "</$ns:results>";
00295                 return implode("\n", $out);
00296         }
00297         
00298         function getInfo(){
00299                 $ns = $this->ns;
00300                 $app =& Dataface_Application::getInstance();
00301                 
00302                 $allowed_fields = array('_auth/auth_type'=>true);
00303                 if ( isset($app->_conf["xml_public_info"]) ){
00304                         $allowed_fields = array_merge($app->_conf['xml_public_info'], $allowed_fields);
00305                 }
00306                 $af = array();
00307                 foreach ($allowed_fields as $key=>$value){
00308                         $path = explode('/', $key);
00309                         if ( count($path) == 1 ){
00310                                 $af[$key] = $value;
00311                         } else {
00312                                 $af[$path[0]][$path[1]] = $value;
00313                         }
00314                         
00315                 }
00316                 
00317                 $out = array();
00318                 $out[] = "<$ns:config>";
00319                 foreach ( $app->_conf as $key=>$value){
00320                         if ( !@$af[$key] ) continue;
00321                         $out[] = "\t<$ns:param><$ns:key>".$this->xmlentities($key)."</$ns:key>";
00322                         if ( is_scalar($value) ){
00323                                 $out[] = "\t\t<$ns:value>".$this->xmlentities($value)."</$ns:value>";
00324                         } else {
00325                                 $out[] = "\t\t<$ns:value>";
00326                                 foreach ($value as $vkey=>$vval){
00327                                         if ( !@$af[$key][$vkey] ) continue;
00328                                         if ( strcasecmp($vkey,'password') === 0 ) continue;
00329                                         $out[] = "\t\t\t<$ns:param><$ns:key>".$this->xmlentities($vkey)."</$ns:key><$ns:value>".$this->xmlentities($vval)."</$ns:value></$ns:param>";
00330                                 }
00331                                 $out[] = "\t\t</$ns:value>";
00332                                 
00333                         }
00334 
00335                         $out[] = "\t</$ns:param>";
00336                 }
00337                 $out[] = "</$ns:config>";
00338                 return implode("\n", $out);
00339         }
00340         
00341         function header(){
00342                 $ns = $this->ns;
00343                 $ans = $this->atts_ns;
00344                 $pns = $this->perms_ns;
00345                 $out = array();
00346                 $app =& Dataface_Application::getInstance();
00347                 header('Content-type: text/xml; charset='.$app->_conf['oe']);
00348                 $out[] = "<?xml version=\"1.0\"?>";
00349                 $out[] = "<dataface_document xmlns:$ns=\"http://www.weblite.ca/dataface/2007/df\" xmlns:$ans=\"http://www.weblite.ca/dataface/2007/dfatts\" xmlns:$pns=\"http://www.weblite.ca/dataface/2007/dfperms\" xmlns:http=\"http://www.weblite.ca/dataface/2007/http\">";
00350                 return implode("\n", $out);
00351         
00352         }
00353         
00354         function footer(){
00355                 
00356                 return $this->requiredTablesToXML()."\n</dataface_document>";
00357         }       
00358         
00359         function xmlentities($string) {
00360                 return str_replace ( array ( '&', '"', "'", '<', '>', '' ), array ( '&amp;' , '&quot;', '&apos;' , '&lt;' , '&gt;', '&apos;' ), $string );
00361         }
00362 }
 All Data Structures Namespaces Files Functions Variables Enumerations