r91457 MediaWiki - Code Review archive

Repository:MediaWiki
Revision:r91456‎ | r91457 | r91458 >
Date:14:16, 5 July 2011
Author:mkroetzsch
Status:deferred
Tags:
Comment:
replace structural blank nodes by named resources and use this to work around the limitations of 4Store's DELETE support (separating SELECT and DELETE would not work with blank nodes)
Modified paths:
  • /trunk/extensions/SemanticMediaWiki/includes/export/SMW_Exporter.php (modified) (history)
  • /trunk/extensions/SemanticMediaWiki/includes/queryprinters/SMW_QP_RDF.php (modified) (history)
  • /trunk/extensions/SemanticMediaWiki/includes/sparql/SMW_SparqlDatabase.php (modified) (history)
  • /trunk/extensions/SemanticMediaWiki/includes/sparql/SMW_SparqlDatabase4Store.php (modified) (history)
  • /trunk/extensions/SemanticMediaWiki/includes/storage/SMW_SparqlStore.php (modified) (history)
  • /trunk/extensions/SemanticMediaWiki/includes/storage/SMW_SparqlStoreQueryEngine.php (modified) (history)

Diff [purge]

Index: trunk/extensions/SemanticMediaWiki/includes/export/SMW_Exporter.php
@@ -45,11 +45,14 @@
4646 * Create exportable data from a given semantic data record.
4747 *
4848 * @param $semdata SMWSemanticData
 49+ * @param $subject mixed SMWDIWikiPage to use as subject, or null to use the one from $semdata
4950 * @return SMWExpData
5051 */
51 - static public function makeExportData( SMWSemanticData $semdata ) {
 52+ static public function makeExportData( SMWSemanticData $semdata, $subject = null ) {
5253 self::initBaseURIs();
53 - $subject = $semdata->getSubject();
 54+ if ( is_null( $subject ) ) {
 55+ $subject = $semdata->getSubject();
 56+ }
5457 if ( $subject->getNamespace() == SMW_NS_PROPERTY ) {
5558 $types = $semdata->getPropertyValues( new SMWDIProperty( '_TYPE' ) );
5659 } else {
@@ -57,7 +60,7 @@
5861 }
5962 $result = self::makeExportDataForSubject( $subject, end( $types ) );
6063 foreach ( $semdata->getProperties() as $property ) {
61 - self::addPropertyValues( $property, $semdata->getPropertyValues( $property ), $result );
 64+ self::addPropertyValues( $property, $semdata->getPropertyValues( $property ), $result, $subject );
6265 }
6366 return $result;
6467 }
@@ -76,51 +79,58 @@
7780 * @param $addStubData boolean to indicate if additional data should be added to make a stub entry for this page
7881 * @return SMWExpData
7982 */
80 - static public function makeExportDataForSubject( SMWDIWikiPage $diWikiPage, $typesvalueforproperty = null, $addStubData = false ) {
 83+ static public function makeExportDataForSubject( SMWDIWikiPage $diWikiPage, $typesvalueforproperty = null, $addStubData = false ) {
8184 global $wgContLang;
82 - $wikiPageExpElement = self::getDataItemExpElement( $diWikiPage );
 85+ $wikiPageExpElement = self::getDataItemExpElement( $diWikiPage, $diWikiPage );
8386 $result = new SMWExpData( $wikiPageExpElement );
8487
85 - $pageTitle = str_replace( '_', ' ', $diWikiPage->getDBkey() );
86 - if ( $diWikiPage->getNamespace() !== 0 ) {
87 - $prefixedSubjectTitle = $wgContLang->getNsText( $diWikiPage->getNamespace()) . ":" . $pageTitle;
 88+ if ( $diWikiPage->getSubobjectName() != '' ) {
 89+ $result->addPropertyObjectValue( self::getSpecialNsResource( 'rdf', 'type' ), self::getSpecialNsResource( 'swivt', 'Subject' ) );
 90+ $masterPage = new SMWDIWikiPage( $diWikiPage->getDBkey(), $diWikiPage->getNamespace(), $diWikiPage->getInterwiki() );
 91+ $masterExpElement = self::getDataItemExpElement( $masterPage, $masterPage );
 92+ $result->addPropertyObjectValue( self::getSpecialNsResource( 'swivt', 'masterPage' ), $masterExpElement );
8893 } else {
89 - $prefixedSubjectTitle = $pageTitle;
90 - }
91 - $prefixedSubjectUrl = wfUrlencode( str_replace( ' ', '_', $prefixedSubjectTitle ) );
 94+ $pageTitle = str_replace( '_', ' ', $diWikiPage->getDBkey() );
 95+ if ( $diWikiPage->getNamespace() !== 0 ) {
 96+ $prefixedSubjectTitle = $wgContLang->getNsText( $diWikiPage->getNamespace()) . ":" . $pageTitle;
 97+ } else {
 98+ $prefixedSubjectTitle = $pageTitle;
 99+ }
 100+ $prefixedSubjectUrl = wfUrlencode( str_replace( ' ', '_', $prefixedSubjectTitle ) );
92101
93 - switch ( $diWikiPage->getNamespace() ) {
94 - case NS_CATEGORY: case SMW_NS_CONCEPT:
95 - $maintype_pe = self::getSpecialNsResource( 'owl', 'Class' );
96 - $label = $pageTitle;
97 - break;
98 - case SMW_NS_PROPERTY:
99 - if ( $typesvalueforproperty == null ) {
100 - $types = smwfGetStore()->getPropertyValues( $diWikiPage, new SMWDIProperty( '_TYPE' ) );
101 - $typesvalueforproperty = end( $types );
102 - }
103 - $maintype_pe = self::getSpecialNsResource( 'owl', self::getOWLPropertyType( $typesvalueforproperty ) );
104 - $label = $pageTitle;
105 - break;
106 - default:
107 - $label = $prefixedSubjectTitle;
108 - $maintype_pe = self::getSpecialNsResource( 'swivt', 'Subject' );
109 - }
 102+ switch ( $diWikiPage->getNamespace() ) {
 103+ case NS_CATEGORY: case SMW_NS_CONCEPT:
 104+ $maintype_pe = self::getSpecialNsResource( 'owl', 'Class' );
 105+ $label = $pageTitle;
 106+ break;
 107+ case SMW_NS_PROPERTY:
 108+ if ( $typesvalueforproperty == null ) {
 109+ $types = smwfGetStore()->getPropertyValues( $diWikiPage, new SMWDIProperty( '_TYPE' ) );
 110+ $typesvalueforproperty = end( $types );
 111+ }
 112+ $maintype_pe = self::getSpecialNsResource( 'owl', self::getOWLPropertyType( $typesvalueforproperty ) );
 113+ $label = $pageTitle;
 114+ break;
 115+ default:
 116+ $label = $prefixedSubjectTitle;
 117+ $maintype_pe = self::getSpecialNsResource( 'swivt', 'Subject' );
 118+ }
110119
111 - $result->addPropertyObjectValue( self::getSpecialNsResource( 'rdf', 'type' ), $maintype_pe );
 120+ $result->addPropertyObjectValue( self::getSpecialNsResource( 'rdf', 'type' ), $maintype_pe );
112121
113 - if ( !$wikiPageExpElement->isBlankNode() ) {
114 - $ed = new SMWExpLiteral( $label );
115 - $result->addPropertyObjectValue( self::getSpecialNsResource( 'rdfs', 'label' ), $ed );
116 - $ed = new SMWExpResource( self::getNamespaceUri( 'wikiurl' ) . $prefixedSubjectUrl );
117 - $result->addPropertyObjectValue( self::getSpecialNsResource( 'swivt', 'page' ), $ed );
118 - $ed = new SMWExpResource( self::$m_exporturl . '/' . $prefixedSubjectUrl );
119 - $result->addPropertyObjectValue( self::getSpecialNsResource( 'rdfs', 'isDefinedBy' ), $ed );
120 - $ed = new SMWExpLiteral( $diWikiPage->getNamespace(), 'http://www.w3.org/2001/XMLSchema#integer' );
121 - $result->addPropertyObjectValue( self::getSpecialNsResource( 'swivt', 'wikiNamespace' ), $ed );
122 - if ( $addStubData ) {
123 - $defaultSortkey = new SMWExpLiteral( str_replace( '_', ' ', $diWikiPage->getDBkey() ) );
124 - $result->addPropertyObjectValue( self::getSpecialPropertyResource( '_SKEY' ), $defaultSortkey );
 122+ if ( !$wikiPageExpElement->isBlankNode() ) {
 123+ $ed = new SMWExpLiteral( $label );
 124+ $result->addPropertyObjectValue( self::getSpecialNsResource( 'rdfs', 'label' ), $ed );
 125+ $ed = new SMWExpResource( self::getNamespaceUri( 'wikiurl' ) . $prefixedSubjectUrl );
 126+ $result->addPropertyObjectValue( self::getSpecialNsResource( 'swivt', 'page' ), $ed );
 127+ $ed = new SMWExpResource( self::$m_exporturl . '/' . $prefixedSubjectUrl );
 128+ $result->addPropertyObjectValue( self::getSpecialNsResource( 'rdfs', 'isDefinedBy' ), $ed );
 129+ $ed = new SMWExpLiteral( $diWikiPage->getNamespace(), 'http://www.w3.org/2001/XMLSchema#integer' );
 130+ $result->addPropertyObjectValue( self::getSpecialNsResource( 'swivt', 'wikiNamespace' ), $ed );
 131+ if ( $addStubData ) {
 132+ $defaultSortkey = new SMWExpLiteral( str_replace( '_', ' ', $diWikiPage->getDBkey() ) );
 133+ $result->addPropertyObjectValue( self::getSpecialPropertyResource( '_SKEY' ), $defaultSortkey );
 134+ }
125135 }
126136 }
127137
@@ -135,13 +145,14 @@
136146 * @param $property SMWDIProperty
137147 * @param $dataItems array of SMWDataItem objects for the given property
138148 * @param $data SMWExpData to add the data to
 149+ * @param $masterPage SMWDIWikiPage to which the data belongs; needed for internal object URIs
139150 */
140 - static public function addPropertyValues( SMWDIProperty $property, array $dataItems, SMWExpData &$expData ) {
 151+ static public function addPropertyValues( SMWDIProperty $property, array $dataItems, SMWExpData &$expData, SMWDIWikiPage $masterPage ) {
141152 if ( $property->isUserDefined() ) {
142153 $pe = self::getResourceElementForProperty( $property );
143154 $peHelper = self::getResourceElementForProperty( $property, true );
144155 foreach ( $dataItems as $dataItem ) {
145 - $ed = self::getDataItemExpElement( $dataItem );
 156+ $ed = self::getDataItemExpElement( $dataItem, $masterPage );
146157 if ( $ed !== null ) {
147158 $expData->addPropertyObjectValue( $pe, $ed );
148159 }
@@ -175,7 +186,7 @@
176187 ( $dataItem->getNamespace() != $diSubject->getNamespace() ) ) ) {
177188 continue;
178189 }
179 - $ed = self::getDataItemExpElement( $dataItem );
 190+ $ed = self::getDataItemExpElement( $dataItem, $masterPage );
180191 if ( $ed !== null ) {
181192 if ( ( $property->getKey() == '_CONC' ) && ( $ed->getSubject()->getUri() == '' ) ) {
182193 // equivalent to anonymous class -> simplify description
@@ -231,7 +242,7 @@
232243 * occuring in MW titles).
233244 *
234245 * @param $diWikiPage SMWDIWikiPage or SMWDIProperty
235 - * @param $modifier string, using only Latin letters
 246+ * @param $modifier string, using only Latin letters and numbers
236247 * @return SMWExpResource
237248 */
238249 static public function getResourceElementForWikiPage( SMWDIWikiPage $diWikiPage, $modifier = '' ) {
@@ -245,6 +256,10 @@
246257 } // else: Medialink to non-existing file :-/ fall through
247258 }
248259
 260+ if ( $diWikiPage->getSubobjectName() != '' ) {
 261+ $modifier = $diWikiPage->getSubobjectName();
 262+ }
 263+
249264 if ( $modifier == '' ) {
250265 $importProperty = new SMWDIProperty( '_IMPO' );
251266 $importDis = smwfGetStore()->getPropertyValues( $diWikiPage, $importProperty );
@@ -273,7 +288,7 @@
274289 $namespace = self::getNamespaceUri( 'wiki' );
275290 $namespaceId = 'wiki';
276291 if ( $diWikiPage->getNamespace() !== 0 ) {
277 - $localName = str_replace( ' ', '_', $wgContLang->getNSText( $diWikiPage->getNamespace() ) ) . ":" . $diWikiPage->getDBkey();
 292+ $localName = str_replace( ' ', '_', $wgContLang->getNSText( $diWikiPage->getNamespace() ) ) . ':' . $diWikiPage->getDBkey();
278293 } else {
279294 $localName = $diWikiPage->getDBkey();
280295 }
@@ -304,9 +319,18 @@
305320 if ( strpos( $uri, $wikiNamespace ) === 0 ) {
306321 $localName = substr( $uri, strlen( $wikiNamespace ) );
307322 $dbKey = urldecode( self::decodeURI( $localName ) );
 323+
 324+ $parts = explode( '-23', $dbKey, 2 );
 325+ if ( count( $parts ) == 2 ) {
 326+ $dbkey = $parts[0];
 327+ $subobjectname = $parts[1];
 328+ } else {
 329+ $subobjectname = '';
 330+ }
 331+
308332 $parts = explode( ':', $dbKey, 2 );
309333 if ( count( $parts ) == 1 ) {
310 - $dataItem = new SMWDIWikiPage( $dbKey, NS_MAIN, '' );
 334+ $dataItem = new SMWDIWikiPage( $dbKey, NS_MAIN, '', $subobjectname );
311335 } else {
312336 // try the by far most common cases directly before using Title
313337 $namespaceName = str_replace( '_', ' ', $parts[0] );
@@ -318,11 +342,11 @@
319343 }
320344 }
321345 if ( $namespaceId != -1 ) {
322 - $dataItem = new SMWDIWikiPage( $parts[1], $namespaceId, '' );
 346+ $dataItem = new SMWDIWikiPage( $parts[1], $namespaceId, '', $subobjectname );
323347 } else {
324348 $title = Title::newFromDBkey( $dbKey );
325349 if ( $title !== null ) {
326 - $dataItem = SMWDIWikiPage::newFromTitle( $title );
 350+ $dataItem = new SMWDIWikiPage( $title->getDBkey(), $title->getNamespace(), $title->getInterwiki(), $subobjectname );
327351 }
328352 }
329353 }
@@ -513,9 +537,10 @@
514538 * SMWExporter::getSpecialPropertyResource().
515539 *
516540 * @param $dataItem SMWDataItem
 541+ * @param $masterPage mixed SMWDIWikiPage to which the data belongs (needed for internal object URIs); or NULL if deemed irrelevant
517542 * @return SMWExpElement
518543 */
519 - static public function getDataItemExpElement( SMWDataItem $dataItem ) {
 544+ static public function getDataItemExpElement( SMWDataItem $dataItem, $masterPage ) {
520545 switch ( $dataItem->getDIType() ) {
521546 case SMWDataItem::TYPE_NUMBER:
522547 $lit = new SMWExpLiteral( $dataItem->getNumber(), 'http://www.w3.org/2001/XMLSchema#double', $dataItem );
@@ -560,7 +585,7 @@
561586 /// TODO
562587 return null;
563588 case SMWDataItem::TYPE_CONTAINER:
564 - return self::makeExportData( $dataItem->getSemanticData() );
 589+ return self::makeExportData( $dataItem->getSemanticData(), $dataItem->getSubjectPage( $masterPage ) );
565590 case SMWDataItem::TYPE_WIKIPAGE:
566591 return self::getResourceElementForWikiPage( $dataItem );
567592 case SMWDataItem::TYPE_CONCEPT:
Index: trunk/extensions/SemanticMediaWiki/includes/queryprinters/SMW_QP_RDF.php
@@ -49,7 +49,8 @@
5050 $serializer->startSerialization();
5151 $serializer->serializeExpData( SMWExporter::getOntologyExpData( '' ) );
5252 while ( $row = $res->getNext() ) {
53 - $data = SMWExporter::makeExportDataForSubject( reset( $row )->getResultSubject() );
 53+ $subjectDi = reset( $row )->getResultSubject();
 54+ $data = SMWExporter::makeExportDataForSubject( $subjectDi );
5455 foreach ( $row as $resultarray ) {
5556 $printreq = $resultarray->getPrintRequest();
5657 $property = null;
@@ -68,7 +69,7 @@
6970 break;
7071 }
7172 if ( $property !== null ) {
72 - SMWExporter::addPropertyValues( $property, $resultarray->getContent() , $data );
 73+ SMWExporter::addPropertyValues( $property, $resultarray->getContent() , $data, $subjectDi );
7374 }
7475 }
7576 $serializer->serializeExpData( $data );
Index: trunk/extensions/SemanticMediaWiki/includes/sparql/SMW_SparqlDatabase.php
@@ -201,7 +201,7 @@
202202 *
203203 * @param $vars mixed array or string, field name(s) to be retrieved, can be '*'
204204 * @param $where string WHERE part of the query, without surrounding { }
205 - * @param $options array (associative) of options, e.g. array('LIMIT' => '10')
 205+ * @param $options array (associative) of options, e.g. array( 'LIMIT' => '10' )
206206 * @param $extraNamespaces array (associative) of namespaceId => namespaceUri
207207 * @return SMWSparqlResultWrapper
208208 */
@@ -318,6 +318,26 @@
319319 }
320320
321321 /**
 322+ * Convenience method for deleting all triples that have a subject that
 323+ * occurs in a triple with the given property and object. This is used
 324+ * in SMW to delete subobjects with all their data. Some RDF stores fail
 325+ * on complex delete queries, hence a wrapper function is provided to
 326+ * allow more pedestrian implementations.
 327+ *
 328+ * The function declares the standard namespaces wiki, swivt, rdf, owl,
 329+ * rdfs, property, xsd, so these do not have to be included in
 330+ * $extraNamespaces.
 331+ *
 332+ * @param $propertyName string Turtle name of marking property
 333+ * @param $objectName string Turtle name of marking object/value
 334+ * @param $extraNamespaces array (associative) of namespaceId => namespaceUri
 335+ * @return boolean stating whether the operations succeeded
 336+ */
 337+ public function deleteContentByValue( $propertyName, $objectName, $extraNamespaces = array() ) {
 338+ return smwfGetSparqlDatabase()->delete( "?s ?p ?o", "?s $propertyName $objectName . ?s ?p ?o" );
 339+ }
 340+
 341+ /**
322342 * INSERT DELETE wrapper.
323343 * The function declares the standard namespaces wiki, swivt, rdf, owl,
324344 * rdfs, property, xsd, so these do not have to be included in
Index: trunk/extensions/SemanticMediaWiki/includes/sparql/SMW_SparqlDatabase4Store.php
@@ -60,6 +60,28 @@
6161 }
6262
6363 /**
 64+ * Complex SPARQL Update delete operations are not supported in 4Store
 65+ * as of v1.1.3, hence this implementation uses a less efficient method
 66+ * for accomplishing this.
 67+ *
 68+ * @param $propertyName string Turtle name of marking property
 69+ * @param $objectName string Turtle name of marking object/value
 70+ * @param $extraNamespaces array (associative) of namespaceId => namespaceUri
 71+ * @return boolean stating whether the operations succeeded
 72+ */
 73+ public function deleteContentByValue( $propertyName, $objectName, $extraNamespaces = array() ) {
 74+ $affectedObjects = $this->select( '*', "?s $propertyName $objectName", array(), $extraNamespaces );
 75+ $success = ( $affectedObjects->getErrorCode() == SMWSparqlResultWrapper::ERROR_NOERROR );
 76+ foreach ( $affectedObjects as $expElements ) {
 77+ if ( count( $expElements ) > 0 ) {
 78+ $turtleName = SMWTurtleSerializer::getTurtleNameForExpElement( reset( $expElements ) );
 79+ $success = $this->delete( "$turtleName ?p ?o", "$turtleName ?p ?o", $extraNamespaces ) && $success;
 80+ }
 81+ }
 82+ return $success;
 83+ }
 84+
 85+ /**
6486 * Execute a HTTP-based SPARQL POST request according to
6587 * http://www.w3.org/2009/sparql/docs/http-rdf-update/.
6688 * The method throws exceptions based on
Index: trunk/extensions/SemanticMediaWiki/includes/storage/SMW_SparqlStoreQueryEngine.php
@@ -811,7 +811,7 @@
812812 } elseif ( $comparator == '=' ) {
813813 $expElement = SMWExporter::getDataItemHelperExpElement( $dataItem );
814814 if ( $expElement === null ) {
815 - $expElement = SMWExporter::getDataItemExpElement( $dataItem );
 815+ $expElement = SMWExporter::getDataItemExpElement( $dataItem, null );
816816 }
817817 $result = new SMWSparqlSingletonCondition( $expElement );
818818 $this->addOrderByDataForProperty( $result, $joinVariable, $orderByProperty, $dataItem->getDIType() );
@@ -831,11 +831,11 @@
832832 $orderByVariable = $result->orderByVariable;
833833
834834 if ( $dataItem instanceof SMWDIWikiPage ) {
835 - $expElement = SMWExporter::getDataItemExpElement( $dataItem->getSortKeyDataItem() );
 835+ $expElement = SMWExporter::getDataItemExpElement( $dataItem->getSortKeyDataItem(), null );
836836 } else {
837837 $expElement = SMWExporter::getDataItemHelperExpElement( $dataItem );
838838 if ( $expElement === null ) {
839 - $expElement = SMWExporter::getDataItemExpElement( $dataItem );
 839+ $expElement = SMWExporter::getDataItemExpElement( $dataItem, null );
840840 }
841841 }
842842
Index: trunk/extensions/SemanticMediaWiki/includes/storage/SMW_SparqlStore.php
@@ -24,16 +24,17 @@
2525
2626 public function deleteSubject( Title $subject ) {
2727 $dataItem = SMWDIWikiPage::newFromTitle( $subject );
28 - $expResource = SMWExporter::getDataItemExpElement( $dataItem );
 28+ $expResource = SMWExporter::getDataItemExpElement( $dataItem, $dataItem );
2929 $this->deleteSparqlData( $expResource );
3030 parent::deleteSubject( $subject );
3131 }
3232
 33+ /// @todo Change master page entries as well
3334 public function changeTitle( Title $oldtitle, Title $newtitle, $pageid, $redirid = 0 ) {
3435 $oldWikiPage = SMWDIWikiPage::newFromTitle( $oldtitle );
3536 $newWikiPage = SMWDIWikiPage::newFromTitle( $newtitle );
36 - $oldExpResource = SMWExporter::getDataItemExpElement( $oldWikiPage );
37 - $newExpResource = SMWExporter::getDataItemExpElement( $newWikiPage );
 37+ $oldExpResource = SMWExporter::getDataItemExpElement( $oldWikiPage, $oldWikiPage );
 38+ $newExpResource = SMWExporter::getDataItemExpElement( $newWikiPage, $newWikiPage );
3839 $namespaces = array( $oldExpResource->getNamespaceId() => $oldExpResource->getNamespace() );
3940 $namespaces[$newExpResource->getNamespaceId()] = $newExpResource->getNamespace();
4041 $oldUri = SMWTurtleSerializer::getTurtleNameForExpElement( $oldExpResource );
@@ -62,7 +63,7 @@
6364 $expDataArray = $this->prepareUpdateExpData( $data );
6465
6566 if ( count( $expDataArray ) > 0 ) {
66 - $subjectResource = SMWExporter::getDataItemExpElement( $data->getSubject() );
 67+ $subjectResource = SMWExporter::getDataItemExpElement( $data->getSubject(), $data->getSubject() );
6768 $this->deleteSparqlData( $subjectResource );
6869
6970 $turtleSerializer = new SMWTurtleSerializer( true );
@@ -95,7 +96,7 @@
9697 protected function prepareUpdateExpData( SMWSemanticData $data ) {
9798 $expData = SMWExporter::makeExportData( $data );
9899 $result = array();
99 - $newExpData = $this->expandUpdateExpData( $expData, $expData->getSubject(), $result, false );
 100+ $newExpData = $this->expandUpdateExpData( $expData, $result, false );
100101 array_unshift( $result, $newExpData );
101102 return $result;
102103 }
@@ -110,15 +111,14 @@
111112 * This auxiliary data is collected in a call-by-ref array.
112113 *
113114 * @param $expElement SMWExpElement object containing the update data
114 - * @param $masterExpElement SMWExpResource to which encountered blank nodes will be associated
115115 * @param $auxiliaryExpData array of SMWExpData
116116 * @return SMWExpElement
117117 */
118 - protected function expandUpdateExpElement( SMWExpElement $expElement, SMWExpResource $masterExpElement, array &$auxiliaryExpData ) {
 118+ protected function expandUpdateExpElement( SMWExpElement $expElement, array &$auxiliaryExpData ) {
119119 if ( $expElement instanceof SMWExpResource ) {
120 - $elementTarget = $this->expandUpdateExpResource( $expElement, $masterExpElement, $auxiliaryExpData );
 120+ $elementTarget = $this->expandUpdateExpResource( $expElement, $auxiliaryExpData );
121121 } elseif ( $expElement instanceof SMWExpData ) {
122 - $elementTarget = $this->expandUpdateExpData( $expElement, $masterExpElement, $auxiliaryExpData, true );
 122+ $elementTarget = $this->expandUpdateExpData( $expElement, $auxiliaryExpData, true );
123123 } else {
124124 $elementTarget = $expElement;
125125 }
@@ -136,11 +136,10 @@
137137 * This auxiliary data is collected in a call-by-ref array.
138138 *
139139 * @param $expResource SMWExpResource object containing the update data
140 - * @param $masterExpElement SMWExpResource to which encountered blank nodes will be associated
141140 * @param $auxiliaryExpData array of SMWExpData
142141 * @return SMWExpElement
143142 */
144 - protected function expandUpdateExpResource( SMWExpResource $expResource, SMWExpResource $masterExpElement, array &$auxiliaryExpData ) {
 143+ protected function expandUpdateExpResource( SMWExpResource $expResource, array &$auxiliaryExpData ) {
145144 $exists = true;
146145 if ( $expResource instanceof SMWExpNsResource ) {
147146 $elementTarget = $this->getSparqlRedirectTarget( $expResource, $exists );
@@ -148,12 +147,7 @@
149148 $elementTarget = $expResource;
150149 }
151150
152 - if ( $elementTarget->isBlankNode() ) {
153 - $auxExpData = new SMWExpData( $elementTarget );
154 - $masterResourceProperty = SMWExporter::getSpecialNsResource( 'swivt', 'masterResource' );
155 - $auxExpData->addPropertyObjectValue( $masterResourceProperty, $masterExpElement );
156 - $elementTarget = $auxExpData;
157 - } elseif ( !$exists && ( $elementTarget->getDataItem() instanceof SMWDIWikiPage ) ) {
 151+ if ( !$exists && ( $elementTarget->getDataItem() instanceof SMWDIWikiPage ) ) {
158152 $diWikiPage = $elementTarget->getDataItem();
159153 $hash = $diWikiPage->getHash();
160154 if ( !array_key_exists( $hash, $auxiliaryExpData ) ) {
@@ -173,15 +167,14 @@
174168 * This auxiliary data is collected in a call-by-ref array.
175169 *
176170 * @param $expData SMWExpData object containing the update data
177 - * @param $masterExpElement SMWExpResource to which encountered blank nodes will be associated
178171 * @param $auxiliaryExpData array of SMWExpData
179172 * @param $expandSubject boolean controls if redirects/auxiliary data should also be sought for subject
180173 * @return SMWExpData
181174 */
182 - protected function expandUpdateExpData( SMWExpData $expData, SMWExpResource $masterExpElement, array &$auxiliaryExpData, $expandSubject ) {
 175+ protected function expandUpdateExpData( SMWExpData $expData, array &$auxiliaryExpData, $expandSubject ) {
183176 $subjectExpResource = $expData->getSubject();
184177 if ( $expandSubject ) {
185 - $expandedExpElement = $this->expandUpdateExpElement( $subjectExpResource, $masterExpElement, $auxiliaryExpData );
 178+ $expandedExpElement = $this->expandUpdateExpElement( $subjectExpResource, $auxiliaryExpData );
186179 if ( $expandedExpElement instanceof SMWExpData ) {
187180 $newExpData = $expandedExpElement;
188181 } else { // instanceof SMWExpResource
@@ -192,9 +185,9 @@
193186 }
194187
195188 foreach ( $expData->getProperties() as $propertyResource ) {
196 - $propertyTarget = $this->expandUpdateExpElement( $propertyResource, $masterExpElement, $auxiliaryExpData );
 189+ $propertyTarget = $this->expandUpdateExpElement( $propertyResource, $auxiliaryExpData );
197190 foreach ( $expData->getValues( $propertyResource ) as $expElement ) {
198 - $elementTarget = $this->expandUpdateExpElement( $expElement, $masterExpElement, $auxiliaryExpData );
 191+ $elementTarget = $this->expandUpdateExpElement( $expElement, $auxiliaryExpData );
199192 $newExpData->addPropertyObjectValue( $propertyTarget, $elementTarget );
200193 }
201194 }
@@ -210,13 +203,17 @@
211204 *
212205 * @param $expNsResource string URI to check
213206 * @param $exists boolean that is set to true if $expNsResource is in the
214 - * store; always false for blank nodes
 207+ * store; always false for blank nodes; always true for subobjects
215208 * @return SMWExpNsResource
216209 */
217210 protected function getSparqlRedirectTarget( SMWExpNsResource $expNsResource, &$exists ) {
218211 if ( $expNsResource->isBlankNode() ) {
219212 $exists = false;
220213 return $expNsResource;
 214+ } elseif ( ( $expNsResource->getDataItem() instanceof SMWDIWikiPage ) &&
 215+ $expNsResource->getDataItem()->getSubobjectName() != '' ) {
 216+ $exists = true;
 217+ return $expNsResource;
221218 }
222219
223220 $resourceUri = SMWTurtleSerializer::getTurtleNameForExpElement( $expNsResource );
@@ -224,7 +221,7 @@
225222 $skeyUri = SMWTurtleSerializer::getTurtleNameForExpElement( SMWExporter::getSpecialPropertyResource( '_SKEY' ) );
226223
227224 $sparqlResult = smwfGetSparqlDatabase()->select( '*',
228 - "$resourceUri $skeyUri ?s OPTIONAL { $resourceUri $skeyUri ?s }",
 225+ "$resourceUri $skeyUri ?s OPTIONAL { $resourceUri $rediUri ?r }",
229226 array( 'LIMIT' => 1 ),
230227 array( $expNsResource->getNamespaceId() => $expNsResource->getNamespace() ) );
231228
@@ -253,10 +250,19 @@
254251 * given resource.
255252 *
256253 * @param $expResource SMWExpResource
 254+ * @return boolean success
257255 */
258256 protected function deleteSparqlData( SMWExpResource $expResource ) {
259257 $resourceUri = SMWTurtleSerializer::getTurtleNameForExpElement( $expResource );
260 - smwfGetSparqlDatabase()->delete( "$resourceUri ?p ?o", "$resourceUri ?p ?o" );
 258+ $masterPageProperty = SMWExporter::getSpecialNsResource( 'swivt', 'masterPage' );
 259+ $masterPagePropertyUri = SMWTurtleSerializer::getTurtleNameForExpElement( $masterPageProperty );
 260+
 261+ $success = smwfGetSparqlDatabase()->deleteContentByValue( $masterPagePropertyUri, $resourceUri );
 262+ if ( $success ) {
 263+ return smwfGetSparqlDatabase()->delete( "$resourceUri ?p ?o", "$resourceUri ?p ?o" );
 264+ } else {
 265+ return false;
 266+ }
261267 }
262268
263269
@@ -284,5 +290,10 @@
285291 }
286292 }
287293
 294+ public function drop( $verbose = true ) {
 295+ parent::drop( $verbose );
 296+ smwfGetSparqlDatabase()->delete( "?s ?p ?o", "?s ?p ?o" );
 297+ }
 298+
288299 }
289300