X-Git-Url: https://git.mxchange.org/?a=blobdiff_plain;f=classes%2FNotice.php;h=ebbd9e0462b7e64cb416c1a1eda7c8fd8076885c;hb=f29daa22b6a7319632b2c3798313f54a6b762a10;hp=44d5adb1b7856d46d5832b0ecdbe5b32594c9bf1;hpb=3a6c98ff164e5c77c5ced29750e2259c815ef0b4;p=quix0rs-gnu-social.git diff --git a/classes/Notice.php b/classes/Notice.php index 44d5adb1b7..ebbd9e0462 100644 --- a/classes/Notice.php +++ b/classes/Notice.php @@ -158,43 +158,14 @@ class Notice extends Managed_DataObject $this->_profile[$this->profile_id] = $profile; } - public function deleteAs(Profile $actor) + public function deleteAs(Profile $actor, $delete_event=true) { - if ($this->getProfile()->sameAs($actor) || $actor->hasRight(Right::DELETEOTHERSNOTICE)) { - return $this->delete(); - } - throw new AuthorizationException('You are not allowed to delete other user\'s notices'); - } - - function delete($useWhere=false) - { - // For auditing purposes, save a record that the notice - // was deleted. - - // @fixme we have some cases where things get re-run and so the - // insert fails. - $deleted = Deleted_notice::getKV('id', $this->id); - - if (!$deleted instanceof Deleted_notice) { - $deleted = Deleted_notice::getKV('uri', $this->uri); - } - - if (!$deleted instanceof Deleted_notice) { - $deleted = new Deleted_notice(); - - $deleted->id = $this->id; - $deleted->profile_id = $this->profile_id; - $deleted->uri = $this->uri; - $deleted->created = $this->created; - $deleted->deleted = common_sql_now(); - - $deleted->insert(); + if (!$this->getProfile()->sameAs($actor) && !$actor->hasRight(Right::DELETEOTHERSNOTICE)) { + throw new AuthorizationException(_('You are not allowed to delete another user\'s notice.')); } if (Event::handle('NoticeDeleteRelated', array($this))) { - // Clear related records - $this->clearReplies(); $this->clearLocation(); $this->clearRepeats(); @@ -202,10 +173,21 @@ class Notice extends Managed_DataObject $this->clearGroupInboxes(); $this->clearFiles(); $this->clearAttentions(); - // NOTE: we don't clear queue items } + $result = null; + if (!$delete_event || Event::handle('DeleteNoticeAsProfile', array($this, $actor, &$result))) { + // If $delete_event is true, we run the event. If the Event then + // returns false it is assumed everything was handled properly + // and the notice was deleted. + $result = $this->delete(); + } + return $result; + } + + public function delete($useWhere=false) + { $result = parent::delete($useWhere); $this->blowOnDelete(); @@ -275,6 +257,11 @@ class Notice extends Managed_DataObject return $this->content; } + public function getRendered() + { + return $this->rendered; + } + /* * Get the original representation URL of this notice. * @@ -298,10 +285,8 @@ class Notice extends Managed_DataObject } } - public function get_object_type($canonical=false) { - return $canonical - ? ActivityObject::canonicalType($this->object_type) - : $this->object_type; + public function getObjectType($canonical=false) { + return ActivityUtils::resolveUri($this->object_type, $canonical); } public static function getByUri($uri) @@ -769,7 +754,7 @@ class Notice extends Managed_DataObject $defaults = array( 'groups' => array(), - 'is_local' => self::LOCAL_PUBLIC, + 'is_local' => $actor->isLocal() ? self::LOCAL_PUBLIC : self::REMOTE, 'mentions' => array(), 'reply_to' => null, 'repeat_of' => null, @@ -789,8 +774,9 @@ class Notice extends Managed_DataObject } extract($options, EXTR_SKIP); + // dupe check $stored = new Notice(); - if (!empty($uri)) { + if (!empty($uri) && !ActivityUtils::compareVerbs($act->verb, array(ActivityVerb::DELETE))) { $stored->uri = $uri; if ($stored->find()) { common_debug('cannot create duplicate Notice URI: '.$stored->uri); @@ -798,6 +784,27 @@ class Notice extends Managed_DataObject } } + $autosource = common_config('public', 'autosource'); + + // Sandboxed are non-false, but not 1, either + if (!$actor->hasRight(Right::PUBLICNOTICE) || + ($source && $autosource && in_array($source, $autosource))) { + // FIXME: ...what about remote nonpublic? Hmmm. That is, if we sandbox remote profiles... + $stored->is_local = Notice::LOCAL_NONPUBLIC; + } else { + $stored->is_local = intval($is_local); + } + + if (!$stored->isLocal()) { + // Only do these checks for non-local notices. Local notices will generate these values later. + if (!common_valid_http_url($url)) { + common_debug('Bad notice URL: ['.$url.'], URI: ['.$uri.']. Cannot link back to original! This is normal for shared notices etc.'); + } + if (empty($uri)) { + throw new ServerException('No URI for remote notice. Cannot accept that.'); + } + } + $stored->profile_id = $actor->id; $stored->source = $source; $stored->uri = $uri; @@ -810,14 +817,6 @@ class Notice extends Managed_DataObject : $act->content; $stored->content = common_strip_html($stored->rendered); - $autosource = common_config('public', 'autosource'); - - // Sandboxed are non-false, but not 1, either - if (!$actor->hasRight(Right::PUBLICNOTICE) || - ($source && $autosource && in_array($source, $autosource))) { - $stored->is_local = Notice::LOCAL_NONPUBLIC; - } - // Maybe a missing act-time should be fatal if the actor is not local? if (!empty($act->time)) { $stored->created = common_sql_date($act->time); @@ -901,11 +900,24 @@ class Notice extends Managed_DataObject $urls[] = $href; } + if (ActivityUtils::compareVerbs($stored->verb, array(ActivityVerb::POST))) { + if (empty($act->objects[0]->type)) { + // Default type for the post verb is 'note', but we know it's + // a 'comment' if it is in reply to something. + $stored->object_type = empty($stored->reply_to) ? ActivityObject::NOTE : ActivityObject::COMMENT; + } else { + //TODO: Is it safe to always return a relative URI? The + // JSON version of ActivityStreams always use it, so we + // should definitely be able to handle it... + $stored->object_type = ActivityUtils::resolveUri($act->objects[0]->type, true); + } + } + if (Event::handle('StartNoticeSave', array(&$stored))) { // XXX: some of these functions write to the DB try { - $stored->insert(); // throws exception on error + $result = $stored->insert(); // throws exception on error if ($notloc instanceof Notice_location) { $notloc->notice_id = $stored->getID(); @@ -917,7 +929,7 @@ class Notice extends Managed_DataObject $object = null; Event::handle('StoreActivityObject', array($act, $stored, $options, &$object)); if (empty($object)) { - throw new ServerException('Unsuccessful call to StoreActivityObject '.$stored->uri . ': '.$act->asString()); + throw new ServerException('Unsuccessful call to StoreActivityObject '.$stored->getUri() . ': '.$act->asString()); } // If it's not part of a conversation, it's the beginning @@ -985,15 +997,13 @@ class Notice extends Managed_DataObject } static public function figureOutScope(Profile $actor, array $groups, $scope=null) { - if (is_null($scope)) { - $scope = self::defaultScope(); - } + $scope = is_null($scope) ? self::defaultScope() : intval($scope); // For private streams try { $user = $actor->getUser(); // FIXME: We can't do bit comparison with == (Legacy StatusNet thing. Let's keep it for now.) - if ($user->private_stream && ($scope == Notice::PUBLIC_SCOPE || $scope == Notice::SITE_SCOPE)) { + if ($user->private_stream && ($scope === Notice::PUBLIC_SCOPE || $scope === Notice::SITE_SCOPE)) { $scope |= Notice::FOLLOWER_SCOPE; } } catch (NoSuchUserException $e) { @@ -2415,7 +2425,7 @@ class Notice extends Managed_DataObject $this->uri = sprintf('%s%s=%d:%s=%s', TagURI::mint(), 'noticeId', $this->id, - 'objectType', $this->get_object_type(true)); + 'objectType', $this->getObjectType(true)); $changed = true; } @@ -2477,8 +2487,13 @@ class Notice extends Managed_DataObject public function isLocal() { - return ($this->is_local == Notice::LOCAL_PUBLIC || - $this->is_local == Notice::LOCAL_NONPUBLIC); + $is_local = intval($this->is_local); + return ($is_local === self::LOCAL_PUBLIC || $is_local === self::LOCAL_NONPUBLIC); + } + + public function getScope() + { + return intval($this->scope); } public function isRepeat() @@ -2671,13 +2686,9 @@ class Notice extends Managed_DataObject protected function _inScope($profile) { - if (!is_null($this->scope)) { - $scope = $this->scope; - } else { - $scope = self::defaultScope(); - } + $scope = is_null($this->scope) ? self::defaultScope() : $this->getScope(); - if ($scope == 0 && !$this->getProfile()->isPrivateStream()) { // Not scoping, so it is public. + if ($scope === 0 && !$this->getProfile()->isPrivateStream()) { // Not scoping, so it is public. return !$this->isHiddenSpam($profile); } @@ -2764,10 +2775,24 @@ class Notice extends Managed_DataObject public function getParent() { + $reply_to_id = null; + if (empty($this->reply_to)) { throw new NoParentNoticeException($this); } - return self::getByID($this->reply_to); + + // The reply_to ID in the table Notice could exist with a number + // however, the replied to notice might not exist in the database. + // Thus we need to catch the exception and throw the NoParentNoticeException else + // the timeline will not display correctly. + try { + $reply_to_id = self::getByID($this->reply_to); + } catch(Exception $e){ + throw new NoParentNoticeException($this); + } + + + return $reply_to_id; } /**