/** * Serialize the given SMWExpData object, possibly recursively with * increased indentation. * * @param $data SMWExpData containing the data to be serialised. * @param $indent string specifying a prefix for indentation (usually a sequence of tabs) */ protected function serializeNestedExpData(SMWExpData $data, $indent) { if (count($data->getProperties()) == 0) { return; // nothing to export } // Avoid posting turtle property declarations already known for the // subject more than once if ($data->getSubject()->getDataItem() !== null && $data->getSubject()->getDataItem()->getNamespace() === SMW_NS_PROPERTY) { $hash = $data->getHash(); $poolCache = InMemoryPoolCache::getInstance()->getPoolCacheFor('turtle.serializer'); if ($poolCache->contains($hash) && $poolCache->fetch($hash)) { return; } $poolCache->save($hash, true); } $this->recordDeclarationTypes($data); $bnode = false; $this->post_ns_buffer .= $indent; if (!$data->getSubject()->isBlankNode()) { $this->serializeExpResource($data->getSubject()); } else { // blank node $bnode = true; $this->post_ns_buffer .= "["; } if ($indent !== '' && !$bnode) { // called to generate a nested descripion; but Turtle cannot nest non-bnode descriptions, do this later $this->subexpdata[] = $data; return; } elseif (!$bnode) { $this->post_ns_buffer .= "\n "; } $firstproperty = true; foreach ($data->getProperties() as $property) { $this->post_ns_buffer .= $firstproperty ? "\t" : " ;\n {$indent}\t"; $firstproperty = false; $prop_decl_queued = false; $class_type_prop = $this->isOWLClassTypeProperty($property); $this->serializeExpResource($property); $firstvalue = true; foreach ($data->getValues($property) as $value) { $this->post_ns_buffer .= $firstvalue ? ' ' : ' , '; $firstvalue = false; if ($value instanceof SMWExpLiteral) { $prop_decl_type = SMW_SERIALIZER_DECL_APROP; $this->serializeExpLiteral($value); } elseif ($value instanceof SMWExpResource) { $prop_decl_type = SMW_SERIALIZER_DECL_OPROP; $this->serializeExpResource($value); } elseif ($value instanceof SMWExpData) { // resource (maybe blank node), could have subdescriptions $prop_decl_type = SMW_SERIALIZER_DECL_OPROP; $collection = $value->getCollection(); if ($collection !== false) { // RDF-style collection (list) $this->post_ns_buffer .= "( "; foreach ($collection as $subvalue) { $this->serializeNestedExpData($subvalue, $indent . "\t\t"); if ($class_type_prop) { $this->requireDeclaration($subvalue->getSubject(), SMW_SERIALIZER_DECL_CLASS); } } $this->post_ns_buffer .= " )"; } else { if ($class_type_prop) { $this->requireDeclaration($value->getSubject(), SMW_SERIALIZER_DECL_CLASS); } if (count($value->getProperties()) > 0) { // resource with data: serialise $this->post_ns_buffer .= "\n"; $this->serializeNestedExpData($value, $indent . "\t\t"); } else { // resource without data: may need to be queued $this->serializeExpResource($value->getSubject()); } } } if (!$prop_decl_queued) { $this->requireDeclaration($property, $prop_decl_type); $prop_decl_queued = true; } } } $this->post_ns_buffer .= ($bnode ? " ]" : " .") . ($indent === '' ? "\n\n" : ''); }