Beispiel #1
0
	protected function loadRelations($reload = false) {
		if ($this->loaded['relations'] && !$reload) return;
		
		if (!$this->id) {
			return;
		}
		
		Z_Core::debug("Loading relations for item $this->id");
		
		$this->loadPrimaryData(false, true);
		
		$itemURI = Zotero_URI::getItemURI($this);
		
		$relations = Zotero_Relations::getByURIs($this->libraryID, $itemURI);
		$relations = array_map(function ($rel) {
			return [$rel->predicate, $rel->object];
		}, $relations);
		
		// Related items are bidirectional, so include any with this item as the object
		$reverseRelations = Zotero_Relations::getByURIs(
			$this->libraryID, false, Zotero_Relations::$relatedItemPredicate, $itemURI
		);
		foreach ($reverseRelations as $rel) {
			$r = [$rel->predicate, $rel->subject];
			// Only add if not already added in other direction
			if (!in_array($r, $relations)) {
				$relations[] = $r;
			}
		}
		
		// Also include any owl:sameAs relations with this item as the object
		// (as sent by client via classic sync)
		$reverseRelations = Zotero_Relations::getByURIs(
			$this->libraryID, false, Zotero_Relations::$linkedObjectPredicate, $itemURI
		);
		foreach ($reverseRelations as $rel) {
			$relations[] = [$rel->predicate, $rel->subject];
		}
		
		// TEMP: Get old-style related items
		//
		// Add related items
		$sql = "SELECT `key` FROM itemRelated IR "
			. "JOIN items I ON (IR.linkedItemID=I.itemID) "
			. "WHERE IR.itemID=?";
		$relatedItemKeys = Zotero_DB::columnQuery($sql, $this->id, Zotero_Shards::getByLibraryID($this->libraryID));
		if ($relatedItemKeys) {
			$prefix = Zotero_URI::getLibraryURI($this->libraryID) . "/items/";
			$predicate = Zotero_Relations::$relatedItemPredicate;
			foreach ($relatedItemKeys as $key) {
				$relations[] = [$predicate, $prefix . $key];
			}
		}
		// Reverse as well
		$sql = "SELECT `key` FROM itemRelated IR JOIN items I USING (itemID) WHERE IR.linkedItemID=?";
		$reverseRelatedItemKeys = Zotero_DB::columnQuery(
			$sql, $this->id, Zotero_Shards::getByLibraryID($this->libraryID)
		);
		if ($reverseRelatedItemKeys) {
			$prefix = Zotero_URI::getLibraryURI($this->libraryID) . "/items/";
			$predicate = Zotero_Relations::$relatedItemPredicate;
			foreach ($reverseRelatedItemKeys as $key) {
				$relations[] = [$predicate, $prefix . $key];
			}
		}
		
		$this->relations = $relations;
		$this->loaded['relations'] = true;
		$this->clearChanged('relations');
	}
Beispiel #2
0
 /**
  * Updates the collection's relations. No separate save of the collection is required.
  *
  * @param object $newRelations Object with predicates as keys and URIs as values
  * @param int $userID User making the change
  */
 public function setRelations($newRelations, $userID)
 {
     if (!$this->_id) {
         throw new Exception('collectionID not set');
     }
     // An empty array is allowed by updateFromJSON()
     if (is_array($newRelations) && empty($newRelations)) {
         $newRelations = new stdClass();
     }
     Zotero_DB::beginTransaction();
     // Get arrays from objects
     $oldRelations = get_object_vars($this->getRelations());
     $newRelations = get_object_vars($newRelations);
     $toAdd = array_diff($newRelations, $oldRelations);
     $toRemove = array_diff($oldRelations, $newRelations);
     if (!$toAdd && !$toRemove) {
         Zotero_DB::commit();
         return false;
     }
     $subject = Zotero_URI::getCollectionURI($this);
     foreach ($toAdd as $predicate => $object) {
         Zotero_Relations::add($this->libraryID, $subject, $predicate, $object);
     }
     foreach ($toRemove as $predicate => $object) {
         $relations = Zotero_Relations::getByURIs($this->libraryID, $subject, $predicate, $object);
         foreach ($relations as $relation) {
             Zotero_Relations::delete($this->libraryID, $relation->key);
         }
     }
     $this->updateVersion($userID);
     Zotero_DB::commit();
     return true;
 }