classId = $moc_id; $this->className = GenadClassList::getInstance($app)->getClassName($moc_id); // extract attribute descriptors $att_desc_ext->extractElement(InputExtractor::EC_BEG, $elem, $value, $attrs); if ($elem != "AttributeDescriptorList") throw new Exception ("Invalid descriptor format."); $att_ctl = $att_desc_ext->extractElement(InputExtractor::EC_BEG, $elem, $value, $attrs); $att_arr = array(); while ($att_ctl != InputExtractor::EC_END) { $ele_ctl = $att_desc_ext->extractElement(InputExtractor::EC_BEG, $elem, $value, $attrs); $att = new GenadAttribute(); while ($ele_ctl != InputExtractor::EC_END) { switch ($elem) { case "entity": $att->setName($value); $name = $value; break; case "props": $att->setAttrProperties(new AttrProperties($value)); break; case "rel_moc": $att->setRelatedClass($value); break; case "typ_cl": $att->setTypeClass($app, $value); $att->setValue(); // set instance with default value break; case "mocd_id": break; default: throw new Exception("Unknown attribute descriptor $elem"); } $ele_ctl = $att_desc_ext->extractElement($ele_ctl, $elem, $value, $attrs); } $att_arr[$name] = $att; $att_ctl = $att_desc_ext->extractElement($att_ctl, $elem, $value, $attrs); } if ($inst_extr == null) { $this->att_list = $att_arr; return; } // extract instance data $inst_extr->getCurrentNodeData($elem, $value, $attrs); $tst_cls_nam = $elem; $this->id = $attrs["id"]; $this->mod = $attrs["mod"]; // check class name (set actual class, if mixed inheritance) if ($tst_cls_nam != $this->className) throw new Exception("Inheritance mismatch: $tst_cls_nam vs. $this->className"); // extract attribute values $cntl = InputExtractor::EC_BEG; while (($cntl = $inst_extr->extractElement($cntl, $elem, $value, $attrs)) != InputExtractor::EC_END) { if (! array_key_exists($elem, $att_arr)) throw new Exception ("Attribute $elem not found in att_arr."); $att = $att_arr[$elem]; $att->setValue($value); if ($att->isList()) { $lst_ctl = $inst_extr->extractElement(InputExtractor::EC_BEG, $dummy, $value, $attrs); $list = array(); while ($lst_ctl != InputExtractor::EC_END) { array_push($list, $value); $lst_ctl = $inst_extr->extractElement($lst_ctl, $dummy, $value, $attrs); } $att->setList($list); } $att_arr[$elem] = $att; } $this->att_list = $att_arr; } public static function load($app, $moc_id, $id = 0) { // $id = 0 means: return empty instance $if = new GenadIf($app); $instanceExtractor = null; if ($id > 0) { $base_class_name = GenadClassList::getInstance($app)->getClassName($moc_id); // fetch instance in advance to check class identity (inheritace!) $inst_doc = $if->getInstance($moc_id, $id); if ($inst_doc === null) throw new Exception("Instance ($moc_id, $id) not existing."); // extract instance identity $instanceExtractor = new XmlExtractor(); $instanceExtractor->openInput($inst_doc); $instanceExtractor->extractElement(InputExtractor::EC_BEG, $elem, $value, $attrs); $tst_cls_nam = $elem; // check class name for inheritance if ($tst_cls_nam != $base_class_name) { $moc_id = GenadClassList::getInstance($app)->getClassId($tst_cls_nam); if (!$moc_id) throw new Exception("Class $tst_cls_nam not found in GenadClassList"); } } $desc_doc = $if->getAttrDescList($moc_id); $desc_extr = new XmlExtractor(); $desc_extr->openInput($desc_doc); return new GenadInstance($app, $moc_id, $desc_extr, $instanceExtractor); } public function getName() { return $this->className; } public function getAttributeList() { return $this->att_list; } public function getId() { return $this->id; } public function getMod() { return $this->mod; } public function getApplication() { return $this->app; } public function getClassId() { return $this->classId; } public function update($var_arr) { // set all bools to false, because "false" is not reported in POST // empty all lists, because empty lists are not reported in POST foreach ($this->att_list as $attribute) { if ($attribute->isBool()) $attribute->setValue("false"); if ($attribute->isList()) $attribute->setValue(0); } // now transfer POST values into instance while ( list($key, $value) = each($var_arr) ) { switch ($key) { case "id": if ($this->id != $value) throw new Exception("id mismatch"); break; case "mod": if ($this->mod != $value) throw new Exception("mod mismatch"); break; default: if (array_key_exists($key, $this->att_list)) { if ($this->att_list[$key]->isList()) { $this->att_list[$key]->setValue(count($value)); $this->att_list[$key]->setList($value); } else $this->att_list[$key]->setValue($value); } } } } // restore reflection classes public function recover() { foreach ($this->att_list as $attribute) { $attribute->recover(); } } public function updateRelatedList($class, $var_arr) { $rel_arr = array(); while ( list($key, $value) = each($var_arr) ) { if ($key > 0) array_push($rel_arr, $key); } // check for relation attribute $att_arr = $this->getAttributeList(); $rel_att_nam = ""; while ( list($att_nam, $att) = each($att_arr) ) { if ($att->getRelatedClass() == $class) $rel_att_nam = $att_nam; } if ($rel_att_nam == "") throw new Exception("Related attribute not found"); $this->att_list[$rel_att_nam]->setValue(count($rel_arr)); $this->att_list[$rel_att_nam]->setList($rel_arr); return $this->att_list[$rel_att_nam]; } public function formatOutput($outputFormatter, $editableOnly) { $outputFormatter->initResult(); $id = $this->id; $mod = $this->mod; if ($id) { // id defined -> instance from DB $inst_id_arr = array("id" => "$id", "mod" => "$mod"); $outputFormatter->formatElement(OutputFormatter::FC_BEG, $this->className, null, $inst_id_arr); } else { // id not defined -> instance to be created $outputFormatter->formatElement(OutputFormatter::FC_BEG, $this->className, null, null); } foreach ($this->att_list as $att_nam => $att) { if ( (!$editableOnly || $att->isEditable()) && (! $att->hasSystemInit())) { if ($att->isList()) { $outputFormatter->formatElement(OutputFormatter::FC_BEG, $att->getName(), $att->getValue()); $list = $att->getList(); for ($i=0; $i<$att->getValue(); $i++) { $xml_att = array("no" => $i+1); $outputFormatter->formatElement(OutputFormatter::FC_SGL, "elem", $list[$i], $xml_att); } $outputFormatter->formatElement(OutputFormatter::FC_END); } else { $outputFormatter->formatElement(OutputFormatter::FC_SGL, $att->getName(), $att->getValue()); } } } $outputFormatter->finish(); } public function resetIdentity() { $this->id = 0; $this->mod = 0; } }