mirror of
https://github.com/openvk/openvk
synced 2024-12-23 00:51:03 +03:00
Improve API (#975)
* Add API for notifications * Add editing methods * Add apis for likes and polls * Add attaching polls * can_edit * Fix getting voters in anonymous posts and use c... ...anBeEditedBy instead of checking user's id
This commit is contained in:
parent
6660cb8d94
commit
71c59023cf
20 changed files with 645 additions and 22 deletions
|
@ -6,12 +6,12 @@ use openvk\Web\Models\Entities\Club;
|
||||||
|
|
||||||
final class Groups extends VKAPIRequestHandler
|
final class Groups extends VKAPIRequestHandler
|
||||||
{
|
{
|
||||||
function get(int $user_id = 0, string $fields = "", int $offset = 0, int $count = 6, bool $online = false): object
|
function get(int $user_id = 0, string $fields = "", int $offset = 0, int $count = 6, bool $online = false, string $filter = "groups"): object
|
||||||
{
|
{
|
||||||
$this->requireUser();
|
$this->requireUser();
|
||||||
|
|
||||||
if($user_id == 0) {
|
if($user_id == 0) {
|
||||||
foreach($this->getUser()->getClubs($offset, false, $count, true) as $club)
|
foreach($this->getUser()->getClubs($offset, $filter == "admin", $count, true) as $club)
|
||||||
$clbs[] = $club;
|
$clbs[] = $club;
|
||||||
$clbsCount = $this->getUser()->getClubCount();
|
$clbsCount = $this->getUser()->getClubCount();
|
||||||
} else {
|
} else {
|
||||||
|
@ -21,7 +21,7 @@ final class Groups extends VKAPIRequestHandler
|
||||||
if(is_null($user))
|
if(is_null($user))
|
||||||
$this->fail(15, "Access denied");
|
$this->fail(15, "Access denied");
|
||||||
|
|
||||||
foreach($user->getClubs($offset, false, $count, true) as $club)
|
foreach($user->getClubs($offset, $filter == "admin", $count, true) as $club)
|
||||||
$clbs[] = $club;
|
$clbs[] = $club;
|
||||||
|
|
||||||
$clbsCount = $user->getClubCount();
|
$clbsCount = $user->getClubCount();
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
<?php declare(strict_types=1);
|
<?php declare(strict_types=1);
|
||||||
namespace openvk\VKAPI\Handlers;
|
namespace openvk\VKAPI\Handlers;
|
||||||
use openvk\Web\Models\Repositories\Users as UsersRepo;
|
use openvk\Web\Models\Repositories\Users as UsersRepo;
|
||||||
use openvk\Web\Models\Repositories\Posts as PostsRepo;
|
use openvk\Web\Models\Repositories\{Posts as PostsRepo, Comments as CommentsRepo, Photos as PhotosRepo, Videos as VideosRepo};
|
||||||
|
|
||||||
final class Likes extends VKAPIRequestHandler
|
final class Likes extends VKAPIRequestHandler
|
||||||
{
|
{
|
||||||
|
@ -68,4 +68,51 @@ final class Likes extends VKAPIRequestHandler
|
||||||
$this->fail(100, "One of the parameters specified was missing or invalid: incorrect type");
|
$this->fail(100, "One of the parameters specified was missing or invalid: incorrect type");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function getList(string $type, int $owner_id, int $item_id, bool $extended = false, int $offset = 0, int $count = 10, bool $skip_own = false)
|
||||||
|
{
|
||||||
|
$this->requireUser();
|
||||||
|
|
||||||
|
$object = NULL;
|
||||||
|
|
||||||
|
switch($type) {
|
||||||
|
case "post":
|
||||||
|
$object = (new PostsRepo)->getPostById($owner_id, $item_id);
|
||||||
|
break;
|
||||||
|
case "comment":
|
||||||
|
$object = (new CommentsRepo)->get($item_id);
|
||||||
|
break;
|
||||||
|
case "photo":
|
||||||
|
$object = (new PhotosRepo)->getByOwnerAndVID($owner_id, $item_id);
|
||||||
|
break;
|
||||||
|
case "video":
|
||||||
|
$object = (new VideosRepo)->getByOwnerAndVID($owner_id, $item_id);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
$this->fail(58, "Invalid type");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(!$object || $object->isDeleted())
|
||||||
|
$this->fail(56, "Invalid postable");
|
||||||
|
|
||||||
|
$res = (object)[
|
||||||
|
"count" => $object->getLikesCount(),
|
||||||
|
"items" => []
|
||||||
|
];
|
||||||
|
|
||||||
|
$likers = array_slice(iterator_to_array($object->getLikers(1, $offset + $count)), $offset);
|
||||||
|
|
||||||
|
foreach($likers as $liker) {
|
||||||
|
if($skip_own && $liker->getId() == $this->getUser()->getId())
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if(!$extended)
|
||||||
|
$res->items[] = $liker->getId();
|
||||||
|
else
|
||||||
|
$res->items[] = $liker->toVkApiStruct();
|
||||||
|
}
|
||||||
|
|
||||||
|
return $res;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -65,7 +65,8 @@ final class Messages extends VKAPIRequestHandler
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
function send(int $user_id = -1, int $peer_id = -1, string $domain = "", int $chat_id = -1, string $user_ids = "", string $message = "", int $sticker_id = -1, int $forGodSakePleaseDoNotReportAboutMyOnlineActivity = 0)
|
function send(int $user_id = -1, int $peer_id = -1, string $domain = "", int $chat_id = -1, string $user_ids = "", string $message = "", int $sticker_id = -1, int $forGodSakePleaseDoNotReportAboutMyOnlineActivity = 0,
|
||||||
|
string $attachment = "") # интересно почему не attachments
|
||||||
{
|
{
|
||||||
$this->requireUser();
|
$this->requireUser();
|
||||||
$this->willExecuteWriteAction();
|
$this->willExecuteWriteAction();
|
||||||
|
@ -79,7 +80,8 @@ final class Messages extends VKAPIRequestHandler
|
||||||
$this->fail(946, "Chats are not implemented");
|
$this->fail(946, "Chats are not implemented");
|
||||||
else if($sticker_id !== -1)
|
else if($sticker_id !== -1)
|
||||||
$this->fail(-151, "Stickers are not implemented");
|
$this->fail(-151, "Stickers are not implemented");
|
||||||
else if(empty($message))
|
|
||||||
|
if(empty($message) && empty($attachment))
|
||||||
$this->fail(100, "Message text is empty or invalid");
|
$this->fail(100, "Message text is empty or invalid");
|
||||||
|
|
||||||
# lol recursion
|
# lol recursion
|
||||||
|
@ -117,6 +119,21 @@ final class Messages extends VKAPIRequestHandler
|
||||||
if(!$msg)
|
if(!$msg)
|
||||||
$this->fail(950, "Internal error");
|
$this->fail(950, "Internal error");
|
||||||
else
|
else
|
||||||
|
if(!empty($attachment)) {
|
||||||
|
$attachs = parseAttachments($attachment);
|
||||||
|
|
||||||
|
# Работают только фотки, остальное просто не будет отображаться.
|
||||||
|
if(sizeof($attachs) >= 10)
|
||||||
|
$this->fail(15, "Too many attachments");
|
||||||
|
|
||||||
|
foreach($attachs as $attach) {
|
||||||
|
if($attach && !$attach->isDeleted() && $attach->getOwner()->getId() == $this->getUser()->getId())
|
||||||
|
$msg->attach($attach);
|
||||||
|
else
|
||||||
|
$this->fail(52, "One of the attachments is invalid");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return $msg->getId();
|
return $msg->getId();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -393,4 +410,49 @@ final class Messages extends VKAPIRequestHandler
|
||||||
|
|
||||||
return $res;
|
return $res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function edit(int $message_id, string $message = "", string $attachment = "", int $peer_id = 0)
|
||||||
|
{
|
||||||
|
$this->requireUser();
|
||||||
|
$this->willExecuteWriteAction();
|
||||||
|
|
||||||
|
$msg = (new MSGRepo)->get($message_id);
|
||||||
|
|
||||||
|
if(empty($message) && empty($attachment))
|
||||||
|
$this->fail(100, "Required parameter 'message' missing.");
|
||||||
|
|
||||||
|
if(!$msg || $msg->isDeleted())
|
||||||
|
$this->fail(102, "Invalid message");
|
||||||
|
|
||||||
|
if($msg->getSender()->getId() != $this->getUser()->getId())
|
||||||
|
$this->fail(15, "Access to message denied");
|
||||||
|
|
||||||
|
if(!empty($message))
|
||||||
|
$msg->setContent($message);
|
||||||
|
|
||||||
|
$msg->setEdited(time());
|
||||||
|
$msg->save(true);
|
||||||
|
|
||||||
|
if(!empty($attachment)) {
|
||||||
|
$attachs = parseAttachments($attachment);
|
||||||
|
$newAttachmentsCount = sizeof($attachs);
|
||||||
|
|
||||||
|
$postsAttachments = iterator_to_array($msg->getChildren());
|
||||||
|
|
||||||
|
if(sizeof($postsAttachments) >= 10)
|
||||||
|
$this->fail(15, "Message have too many attachments");
|
||||||
|
|
||||||
|
if(($newAttachmentsCount + sizeof($postsAttachments)) > 10)
|
||||||
|
$this->fail(158, "Message will have too many attachments");
|
||||||
|
|
||||||
|
foreach($attachs as $attach) {
|
||||||
|
if($attach && !$attach->isDeleted() && $attach->getOwner()->getId() == $this->getUser()->getId())
|
||||||
|
$msg->attach($attach);
|
||||||
|
else
|
||||||
|
$this->fail(52, "One of the attachments is invalid");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -161,19 +161,17 @@ final class Notes extends VKAPIRequestHandler
|
||||||
|
|
||||||
function editComment(int $comment_id, string $message, int $owner_id = NULL)
|
function editComment(int $comment_id, string $message, int $owner_id = NULL)
|
||||||
{
|
{
|
||||||
/*
|
|
||||||
$this->requireUser();
|
$this->requireUser();
|
||||||
$this->willExecuteWriteAction();
|
$this->willExecuteWriteAction();
|
||||||
|
|
||||||
$comment = (new CommentsRepo)->get($comment_id);
|
$comment = (new CommentsRepo)->get($comment_id);
|
||||||
|
|
||||||
if($comment->getOwner() != $this->getUser()->getId())
|
if($comment->getOwner()->getId() != $this->getUser()->getId())
|
||||||
$this->fail(15, "Access to comment denied");
|
$this->fail(15, "Access to comment denied");
|
||||||
|
|
||||||
$comment->setContent($message);
|
$comment->setContent($message);
|
||||||
$comment->setEdited(time());
|
$comment->setEdited(time());
|
||||||
$comment->save();
|
$comment->save(true);
|
||||||
*/
|
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
83
VKAPI/Handlers/Notifications.php
Normal file
83
VKAPI/Handlers/Notifications.php
Normal file
|
@ -0,0 +1,83 @@
|
||||||
|
<?php declare(strict_types=1);
|
||||||
|
namespace openvk\VKAPI\Handlers;
|
||||||
|
use openvk\Web\Models\Entities\Club;
|
||||||
|
use openvk\Web\Models\Repositories\{Notifications as Notifs, Clubs, Users};
|
||||||
|
|
||||||
|
final class Notifications extends VKAPIRequestHandler
|
||||||
|
{
|
||||||
|
function get(int $count = 10,
|
||||||
|
string $from = "",
|
||||||
|
int $offset = 0,
|
||||||
|
string $start_from = "",
|
||||||
|
string $filters = "",
|
||||||
|
int $start_time = 0,
|
||||||
|
int $end_time = 0,
|
||||||
|
int $archived = 0)
|
||||||
|
{
|
||||||
|
$this->requireUser();
|
||||||
|
|
||||||
|
$res = (object)[
|
||||||
|
"items" => [],
|
||||||
|
"profiles" => [],
|
||||||
|
"groups" => [],
|
||||||
|
"last_viewed" => $this->getUser()->getNotificationOffset()
|
||||||
|
];
|
||||||
|
|
||||||
|
if($count > 100)
|
||||||
|
$this->fail(125, "Count is too big");
|
||||||
|
|
||||||
|
if(!eventdb())
|
||||||
|
$this->fail(1289, "EventDB is disabled on this instance");
|
||||||
|
|
||||||
|
$notifs = array_slice(iterator_to_array((new Notifs)->getNotificationsByUser($this->getUser(), $this->getUser()->getNotificationOffset(), (bool)$archived, 1, $offset + $count)), $offset);
|
||||||
|
$tmpProfiles = [];
|
||||||
|
foreach($notifs as $notif) {
|
||||||
|
$sxModel = $notif->getModel(1);
|
||||||
|
|
||||||
|
if(!method_exists($sxModel, "getAvatarUrl"))
|
||||||
|
$sxModel = $notif->getModel(0);
|
||||||
|
|
||||||
|
|
||||||
|
$tmpProfiles[] = $sxModel instanceof Club ? $sxModel->getId() * -1 : $sxModel->getId();
|
||||||
|
$res->items[] = $notif->toVkApiStruct();
|
||||||
|
}
|
||||||
|
|
||||||
|
foreach(array_unique($tmpProfiles) as $id) {
|
||||||
|
if($id > 0) {
|
||||||
|
$sxModel = (new Users)->get($id);
|
||||||
|
$result = (object)[
|
||||||
|
"uid" => $sxModel->getId(),
|
||||||
|
"first_name" => $sxModel->getFirstName(),
|
||||||
|
"last_name" => $sxModel->getLastName(),
|
||||||
|
"photo" => $sxModel->getAvatarUrl(),
|
||||||
|
"photo_medium_rec" => $sxModel->getAvatarUrl("tiny"),
|
||||||
|
"screen_name" => $sxModel->getShortCode()
|
||||||
|
];
|
||||||
|
|
||||||
|
$res->profiles[] = $result;
|
||||||
|
} else {
|
||||||
|
$sxModel = (new Clubs)->get(abs($id));
|
||||||
|
$result = $sxModel->toVkApiStruct($this->getUser());
|
||||||
|
|
||||||
|
$res->groups[] = $result;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return $res;
|
||||||
|
}
|
||||||
|
|
||||||
|
function markAsViewed()
|
||||||
|
{
|
||||||
|
$this->requireUser();
|
||||||
|
$this->willExecuteWriteAction();
|
||||||
|
|
||||||
|
try {
|
||||||
|
$this->getUser()->updateNotificationOffset();
|
||||||
|
$this->getUser()->save();
|
||||||
|
} catch(\Throwable $e) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
}
|
|
@ -104,4 +104,67 @@ final class Polls extends VKAPIRequestHandler
|
||||||
$this->fail(8, "how.to. ook.bacon.in.microwova.");
|
$this->fail(8, "how.to. ook.bacon.in.microwova.");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function getVoters(int $poll_id, int $answer_ids, int $offset = 0, int $count = 6)
|
||||||
|
{
|
||||||
|
$this->requireUser();
|
||||||
|
|
||||||
|
$poll = (new PollsRepo)->get($poll_id);
|
||||||
|
|
||||||
|
if(!$poll)
|
||||||
|
$this->fail(251, "Invalid poll");
|
||||||
|
|
||||||
|
if($poll->isAnonymous())
|
||||||
|
$this->fail(251, "Access denied: poll is anonymous.");
|
||||||
|
|
||||||
|
$voters = array_slice($poll->getVoters($answer_ids, 1, $offset + $count), $offset);
|
||||||
|
$res = (object)[
|
||||||
|
"answer_id" => $answer_ids,
|
||||||
|
"users" => []
|
||||||
|
];
|
||||||
|
|
||||||
|
foreach($voters as $voter)
|
||||||
|
$res->users[] = $voter->toVkApiStruct();
|
||||||
|
|
||||||
|
return $res;
|
||||||
|
}
|
||||||
|
|
||||||
|
function create(string $question, string $add_answers, bool $disable_unvote = false, bool $is_anonymous = false, bool $is_multiple = false, int $end_date = 0)
|
||||||
|
{
|
||||||
|
$this->requireUser();
|
||||||
|
$this->willExecuteWriteAction();
|
||||||
|
|
||||||
|
$options = json_decode($add_answers);
|
||||||
|
|
||||||
|
if(!$options || empty($options))
|
||||||
|
$this->fail(62, "Invalid options");
|
||||||
|
|
||||||
|
if(sizeof($options) > ovkGetQuirk("polls.max-opts"))
|
||||||
|
$this->fail(51, "Too many options");
|
||||||
|
|
||||||
|
$poll = new Poll;
|
||||||
|
$poll->setOwner($this->getUser());
|
||||||
|
$poll->setTitle($question);
|
||||||
|
$poll->setMultipleChoice($is_multiple);
|
||||||
|
$poll->setAnonymity($is_anonymous);
|
||||||
|
$poll->setRevotability(!$disable_unvote);
|
||||||
|
$poll->setOptions($options);
|
||||||
|
|
||||||
|
if($end_date > time()) {
|
||||||
|
if($end_date > time() + (DAY * 365))
|
||||||
|
$this->fail(89, "End date is too big");
|
||||||
|
|
||||||
|
$poll->setEndDate($end_date);
|
||||||
|
}
|
||||||
|
|
||||||
|
$poll->save();
|
||||||
|
|
||||||
|
return $this->getById($poll->getId());
|
||||||
|
}
|
||||||
|
|
||||||
|
function edit()
|
||||||
|
{
|
||||||
|
#todo
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,7 +1,8 @@
|
||||||
<?php declare(strict_types=1);
|
<?php declare(strict_types=1);
|
||||||
namespace openvk\VKAPI\Handlers;
|
namespace openvk\VKAPI\Handlers;
|
||||||
use openvk\Web\Models\Entities\User;
|
use openvk\Web\Models\Entities\{User, Report};
|
||||||
use openvk\Web\Models\Repositories\Users as UsersRepo;
|
use openvk\Web\Models\Repositories\Users as UsersRepo;
|
||||||
|
use openvk\Web\Models\Repositories\Reports;
|
||||||
|
|
||||||
final class Users extends VKAPIRequestHandler
|
final class Users extends VKAPIRequestHandler
|
||||||
{
|
{
|
||||||
|
@ -307,4 +308,26 @@ final class Users extends VKAPIRequestHandler
|
||||||
"items" => $this->get(implode(',', $array), $nfilds, $offset, $count)
|
"items" => $this->get(implode(',', $array), $nfilds, $offset, $count)
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function report(int $user_id, string $type = "spam", string $comment = "")
|
||||||
|
{
|
||||||
|
$this->requireUser();
|
||||||
|
$this->willExecuteWriteAction();
|
||||||
|
|
||||||
|
if($user_id == $this->getUser()->getId())
|
||||||
|
$this->fail(12, "Can't report yourself.");
|
||||||
|
|
||||||
|
if(sizeof(iterator_to_array((new Reports)->getDuplicates("user", $user_id, NULL, $this->getUser()->getId()))) > 0)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
$report = new Report;
|
||||||
|
$report->setUser_id($this->getUser()->getId());
|
||||||
|
$report->setTarget_id($user_id);
|
||||||
|
$report->setType("user");
|
||||||
|
$report->setReason($comment);
|
||||||
|
$report->setCreated(time());
|
||||||
|
$report->save();
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,7 +28,7 @@ abstract class VKAPIRequestHandler
|
||||||
|
|
||||||
protected function getPlatform(): ?string
|
protected function getPlatform(): ?string
|
||||||
{
|
{
|
||||||
return $this->platform;
|
return $this->platform ?? "";
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function userAuthorized(): bool
|
protected function userAuthorized(): bool
|
||||||
|
|
|
@ -11,11 +11,11 @@ use openvk\Web\Models\Repositories\Comments as CommentsRepo;
|
||||||
|
|
||||||
final class Video extends VKAPIRequestHandler
|
final class Video extends VKAPIRequestHandler
|
||||||
{
|
{
|
||||||
function get(int $owner_id, string $videos, int $offset = 0, int $count = 30, int $extended = 0): object
|
function get(int $owner_id, string $videos = "", int $offset = 0, int $count = 30, int $extended = 0): object
|
||||||
{
|
{
|
||||||
$this->requireUser();
|
$this->requireUser();
|
||||||
|
|
||||||
if ($videos) {
|
if(!empty($videos)) {
|
||||||
$vids = explode(',', $videos);
|
$vids = explode(',', $videos);
|
||||||
|
|
||||||
foreach($vids as $vid)
|
foreach($vids as $vid)
|
||||||
|
|
|
@ -15,6 +15,7 @@ use openvk\Web\Models\Entities\Video;
|
||||||
use openvk\Web\Models\Repositories\Videos as VideosRepo;
|
use openvk\Web\Models\Repositories\Videos as VideosRepo;
|
||||||
use openvk\Web\Models\Entities\Note;
|
use openvk\Web\Models\Entities\Note;
|
||||||
use openvk\Web\Models\Repositories\Notes as NotesRepo;
|
use openvk\Web\Models\Repositories\Notes as NotesRepo;
|
||||||
|
use openvk\Web\Models\Repositories\Polls as PollsRepo;
|
||||||
use openvk\Web\Models\Repositories\Audios as AudiosRepo;
|
use openvk\Web\Models\Repositories\Audios as AudiosRepo;
|
||||||
|
|
||||||
final class Wall extends VKAPIRequestHandler
|
final class Wall extends VKAPIRequestHandler
|
||||||
|
@ -125,7 +126,7 @@ final class Wall extends VKAPIRequestHandler
|
||||||
"post_type" => "post",
|
"post_type" => "post",
|
||||||
"text" => $post->getText(false),
|
"text" => $post->getText(false),
|
||||||
"copy_history" => $repost,
|
"copy_history" => $repost,
|
||||||
"can_edit" => 0, # TODO
|
"can_edit" => $post->canBeEditedBy($this->getUser()),
|
||||||
"can_delete" => $post->canBeDeletedBy($this->getUser()),
|
"can_delete" => $post->canBeDeletedBy($this->getUser()),
|
||||||
"can_pin" => $post->canBePinnedBy($this->getUser()),
|
"can_pin" => $post->canBePinnedBy($this->getUser()),
|
||||||
"can_archive" => false, # TODO MAYBE
|
"can_archive" => false, # TODO MAYBE
|
||||||
|
@ -305,7 +306,7 @@ final class Wall extends VKAPIRequestHandler
|
||||||
"post_type" => "post",
|
"post_type" => "post",
|
||||||
"text" => $post->getText(false),
|
"text" => $post->getText(false),
|
||||||
"copy_history" => $repost,
|
"copy_history" => $repost,
|
||||||
"can_edit" => 0, # TODO
|
"can_edit" => $post->canBeEditedBy($this->getUser()),
|
||||||
"can_delete" => $post->canBeDeletedBy($user),
|
"can_delete" => $post->canBeDeletedBy($user),
|
||||||
"can_pin" => $post->canBePinnedBy($user),
|
"can_pin" => $post->canBePinnedBy($user),
|
||||||
"can_archive" => false, # TODO MAYBE
|
"can_archive" => false, # TODO MAYBE
|
||||||
|
@ -444,6 +445,7 @@ final class Wall extends VKAPIRequestHandler
|
||||||
$this->fail(100, "One of the parameters specified was missing or invalid");
|
$this->fail(100, "One of the parameters specified was missing or invalid");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# TODO use parseAttachments
|
||||||
if(!empty($attachments)) {
|
if(!empty($attachments)) {
|
||||||
$attachmentsArr = explode(",", $attachments);
|
$attachmentsArr = explode(",", $attachments);
|
||||||
# Аттачи такого вида: [тип][id владельца]_[id вложения]
|
# Аттачи такого вида: [тип][id владельца]_[id вложения]
|
||||||
|
@ -452,6 +454,10 @@ final class Wall extends VKAPIRequestHandler
|
||||||
if(sizeof($attachmentsArr) > 10)
|
if(sizeof($attachmentsArr) > 10)
|
||||||
$this->fail(50, "Error: too many attachments");
|
$this->fail(50, "Error: too many attachments");
|
||||||
|
|
||||||
|
preg_match_all("/poll/m", $attachments, $matches, PREG_SET_ORDER, 0);
|
||||||
|
if(sizeof($matches) > 1)
|
||||||
|
$this->fail(85, "Error: too many polls");
|
||||||
|
|
||||||
foreach($attachmentsArr as $attac) {
|
foreach($attachmentsArr as $attac) {
|
||||||
$attachmentType = NULL;
|
$attachmentType = NULL;
|
||||||
|
|
||||||
|
@ -461,8 +467,11 @@ final class Wall extends VKAPIRequestHandler
|
||||||
$attachmentType = "video";
|
$attachmentType = "video";
|
||||||
elseif(str_contains($attac, "note"))
|
elseif(str_contains($attac, "note"))
|
||||||
$attachmentType = "note";
|
$attachmentType = "note";
|
||||||
|
elseif(str_contains($attac, "poll"))
|
||||||
|
$attachmentType = "poll";
|
||||||
elseif(str_contains($attac, "audio"))
|
elseif(str_contains($attac, "audio"))
|
||||||
$attachmentType = "audio";
|
$attachmentType = "audio";
|
||||||
|
|
||||||
else
|
else
|
||||||
$this->fail(205, "Unknown attachment type");
|
$this->fail(205, "Unknown attachment type");
|
||||||
|
|
||||||
|
@ -497,6 +506,13 @@ final class Wall extends VKAPIRequestHandler
|
||||||
$this->fail(11, "Access to note denied");
|
$this->fail(11, "Access to note denied");
|
||||||
|
|
||||||
$post->attach($attacc);
|
$post->attach($attacc);
|
||||||
|
} elseif($attachmentType == "poll") {
|
||||||
|
$attacc = (new PollsRepo)->get($attachmentId);
|
||||||
|
|
||||||
|
if(!$attacc || $attacc->isDeleted())
|
||||||
|
$this->fail(100, "Poll does not exist");
|
||||||
|
if($attacc->getOwner()->getId() != $this->getUser()->getId())
|
||||||
|
$this->fail(43, "You do not have access to this poll");
|
||||||
} elseif($attachmentType == "audio") {
|
} elseif($attachmentType == "audio") {
|
||||||
$attacc = (new AudiosRepo)->getByOwnerAndVID($attachmentOwner, $attachmentId);
|
$attacc = (new AudiosRepo)->getByOwnerAndVID($attachmentOwner, $attachmentId);
|
||||||
if(!$attacc || $attacc->isDeleted())
|
if(!$attacc || $attacc->isDeleted())
|
||||||
|
@ -813,6 +829,95 @@ final class Wall extends VKAPIRequestHandler
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function edit(int $owner_id, int $post_id, string $message = "", string $attachments = "") {
|
||||||
|
$this->requireUser();
|
||||||
|
$this->willExecuteWriteAction();
|
||||||
|
|
||||||
|
$post = (new PostsRepo)->getPostById($owner_id, $post_id);
|
||||||
|
|
||||||
|
if(!$post || $post->isDeleted())
|
||||||
|
$this->fail(102, "Invalid post");
|
||||||
|
|
||||||
|
if(empty($message) && empty($attachments))
|
||||||
|
$this->fail(100, "Required parameter 'message' missing.");
|
||||||
|
|
||||||
|
if(!$post->canBeEditedBy($this->getUser()))
|
||||||
|
$this->fail(7, "Access to editing denied");
|
||||||
|
|
||||||
|
if(!empty($message))
|
||||||
|
$post->setContent($message);
|
||||||
|
|
||||||
|
$post->setEdited(time());
|
||||||
|
$post->save(true);
|
||||||
|
|
||||||
|
# todo добавить такое в веб версию
|
||||||
|
if(!empty($attachments)) {
|
||||||
|
$attachs = parseAttachments($attachments);
|
||||||
|
$newAttachmentsCount = sizeof($attachs);
|
||||||
|
|
||||||
|
$postsAttachments = iterator_to_array($post->getChildren());
|
||||||
|
|
||||||
|
if(sizeof($postsAttachments) >= 10)
|
||||||
|
$this->fail(15, "Post have too many attachments");
|
||||||
|
|
||||||
|
if(($newAttachmentsCount + sizeof($postsAttachments)) > 10)
|
||||||
|
$this->fail(158, "Post will have too many attachments");
|
||||||
|
|
||||||
|
foreach($attachs as $attach) {
|
||||||
|
if($attach && !$attach->isDeleted() && $attach->getOwner()->getId() == $this->getUser()->getId())
|
||||||
|
$post->attach($attach);
|
||||||
|
else
|
||||||
|
$this->fail(52, "One of the attachments is invalid");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return ["post_id" => $post->getVirtualId()];
|
||||||
|
}
|
||||||
|
|
||||||
|
function editComment(int $comment_id, int $owner_id = 0, string $message = "", string $attachments = "") {
|
||||||
|
$this->requireUser();
|
||||||
|
$this->willExecuteWriteAction();
|
||||||
|
|
||||||
|
$comment = (new CommentsRepo)->get($comment_id);
|
||||||
|
|
||||||
|
if(empty($message) && empty($attachments))
|
||||||
|
$this->fail(100, "Required parameter 'message' missing.");
|
||||||
|
|
||||||
|
if(!$comment || $comment->isDeleted())
|
||||||
|
$this->fail(102, "Invalid comment");
|
||||||
|
|
||||||
|
if(!$comment->canBeEditedBy($this->getUser()))
|
||||||
|
$this->fail(15, "Access to editing comment denied");
|
||||||
|
|
||||||
|
if(!empty($message))
|
||||||
|
$comment->setContent($message);
|
||||||
|
|
||||||
|
$comment->setEdited(time());
|
||||||
|
$comment->save(true);
|
||||||
|
|
||||||
|
if(!empty($attachments)) {
|
||||||
|
$attachs = parseAttachments($attachments);
|
||||||
|
$newAttachmentsCount = sizeof($attachs);
|
||||||
|
|
||||||
|
$postsAttachments = iterator_to_array($comment->getChildren());
|
||||||
|
|
||||||
|
if(sizeof($postsAttachments) >= 10)
|
||||||
|
$this->fail(15, "Post have too many attachments");
|
||||||
|
|
||||||
|
if(($newAttachmentsCount + sizeof($postsAttachments)) > 10)
|
||||||
|
$this->fail(158, "Post will have too many attachments");
|
||||||
|
|
||||||
|
foreach($attachs as $attach) {
|
||||||
|
if($attach && !$attach->isDeleted() && $attach->getOwner()->getId() == $this->getUser()->getId())
|
||||||
|
$comment->attach($attach);
|
||||||
|
else
|
||||||
|
$this->fail(52, "One of the attachments is invalid");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
private function getApiPhoto($attachment) {
|
private function getApiPhoto($attachment) {
|
||||||
return [
|
return [
|
||||||
"type" => "photo",
|
"type" => "photo",
|
||||||
|
|
|
@ -397,7 +397,7 @@ class Club extends RowModel
|
||||||
|
|
||||||
function toVkApiStruct(?User $user = NULL): object
|
function toVkApiStruct(?User $user = NULL): object
|
||||||
{
|
{
|
||||||
$res = (object)[];
|
$res = (object) [];
|
||||||
|
|
||||||
$res->id = $this->getId();
|
$res->id = $this->getId();
|
||||||
$res->name = $this->getName();
|
$res->name = $this->getName();
|
||||||
|
|
|
@ -91,6 +91,19 @@ class Comment extends Post
|
||||||
return "/wall" . $this->getTarget()->getPrettyId() . "#_comment" . $this->getId();
|
return "/wall" . $this->getTarget()->getPrettyId() . "#_comment" . $this->getId();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function toNotifApiStruct()
|
||||||
|
{
|
||||||
|
$res = (object)[];
|
||||||
|
|
||||||
|
$res->id = $this->getId();
|
||||||
|
$res->owner_id = $this->getOwner()->getId();
|
||||||
|
$res->date = $this->getPublicationTime()->timestamp();
|
||||||
|
$res->text = $this->getText(false);
|
||||||
|
$res->post = NULL; # todo
|
||||||
|
|
||||||
|
return $res;
|
||||||
|
}
|
||||||
|
|
||||||
function canBeEditedBy(?User $user = NULL): bool
|
function canBeEditedBy(?User $user = NULL): bool
|
||||||
{
|
{
|
||||||
if(!$user)
|
if(!$user)
|
||||||
|
|
|
@ -123,7 +123,11 @@ class Message extends RowModel
|
||||||
],
|
],
|
||||||
];
|
];
|
||||||
} else {
|
} else {
|
||||||
throw new \Exception("Unknown attachment type: " . get_class($attachment));
|
$attachments[] = [
|
||||||
|
"type" => "unknown"
|
||||||
|
];
|
||||||
|
|
||||||
|
# throw new \Exception("Unknown attachment type: " . get_class($attachment));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -131,7 +131,7 @@ class Note extends Postable
|
||||||
$res->date = $this->getPublicationTime()->timestamp();
|
$res->date = $this->getPublicationTime()->timestamp();
|
||||||
$res->comments = $this->getCommentsCount();
|
$res->comments = $this->getCommentsCount();
|
||||||
$res->read_comments = $this->getCommentsCount();
|
$res->read_comments = $this->getCommentsCount();
|
||||||
$res->view_url = "/note".$this->getOwner()->getId()."_".$this->getId();
|
$res->view_url = "/note".$this->getOwner()->getId()."_".$this->getVirtualId();
|
||||||
$res->privacy_view = 1;
|
$res->privacy_view = 1;
|
||||||
$res->can_comment = 1;
|
$res->can_comment = 1;
|
||||||
$res->text_wiki = "r";
|
$res->text_wiki = "r";
|
||||||
|
|
|
@ -132,4 +132,138 @@ QUERY;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function getVkApiInfo()
|
||||||
|
{
|
||||||
|
$origin_m = $this->encodeType($this->originModel);
|
||||||
|
$target_m = $this->encodeType($this->targetModel);
|
||||||
|
|
||||||
|
$info = [
|
||||||
|
"type" => "",
|
||||||
|
"parent" => NULL,
|
||||||
|
"feedback" => NULL,
|
||||||
|
];
|
||||||
|
|
||||||
|
switch($this->getActionCode()) {
|
||||||
|
case 0:
|
||||||
|
$info["type"] = "like_post";
|
||||||
|
$info["parent"] = $this->getModel(0)->toNotifApiStruct();
|
||||||
|
$info["feedback"] = $this->getModel(1)->toVkApiStruct();
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
$info["type"] = "copy_post";
|
||||||
|
$info["parent"] = $this->getModel(0)->toNotifApiStruct();
|
||||||
|
$info["feedback"] = NULL; # todo
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
switch($origin_m) {
|
||||||
|
case 19:
|
||||||
|
$info["type"] = "comment_video";
|
||||||
|
$info["parent"] = $this->getModel(0)->toNotifApiStruct();
|
||||||
|
$info["feedback"] = NULL; # айди коммента не сохраняется в бд( ну пиздец блять
|
||||||
|
break;
|
||||||
|
case 13:
|
||||||
|
$info["type"] = "comment_photo";
|
||||||
|
$info["parent"] = $this->getModel(0)->toNotifApiStruct();
|
||||||
|
$info["feedback"] = NULL;
|
||||||
|
break;
|
||||||
|
# unstandart (vk forgor about notes)
|
||||||
|
case 10:
|
||||||
|
$info["type"] = "comment_note";
|
||||||
|
$info["parent"] = $this->getModel(0)->toVkApiStruct();
|
||||||
|
$info["feedback"] = NULL;
|
||||||
|
break;
|
||||||
|
case 14:
|
||||||
|
$info["type"] = "comment_post";
|
||||||
|
$info["parent"] = $this->getModel(0)->toNotifApiStruct();
|
||||||
|
$info["feedback"] = NULL;
|
||||||
|
break;
|
||||||
|
# unused (users don't have topics bruh)
|
||||||
|
case 21:
|
||||||
|
$info["type"] = "comment_topic";
|
||||||
|
$info["parent"] = $this->getModel(0)->toVkApiStruct(0, 90);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
$info["type"] = "comment_unknown";
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
$info["type"] = "wall";
|
||||||
|
$info["feedback"] = $this->getModel(0)->toNotifApiStruct();
|
||||||
|
break;
|
||||||
|
case 4:
|
||||||
|
switch($target_m) {
|
||||||
|
case 14:
|
||||||
|
$info["type"] = "mention";
|
||||||
|
$info["feedback"] = $this->getModel(1)->toNotifApiStruct();
|
||||||
|
break;
|
||||||
|
case 19:
|
||||||
|
$info["type"] = "mention_comment_video";
|
||||||
|
$info["parent"] = $this->getModel(1)->toNotifApiStruct();
|
||||||
|
break;
|
||||||
|
case 13:
|
||||||
|
$info["type"] = "mention_comment_photo";
|
||||||
|
$info["parent"] = $this->getModel(1)->toNotifApiStruct();
|
||||||
|
break;
|
||||||
|
# unstandart
|
||||||
|
case 10:
|
||||||
|
$info["type"] = "mention_comment_note";
|
||||||
|
$info["parent"] = $this->getModel(1)->toVkApiStruct();
|
||||||
|
break;
|
||||||
|
case 21:
|
||||||
|
$info["type"] = "mention_comments";
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
$info["type"] = "mention_comment_unknown";
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case 5:
|
||||||
|
$info["type"] = "make_you_admin";
|
||||||
|
$info["parent"] = $this->getModel(0)->toVkApiStruct($this->getModel(1));
|
||||||
|
break;
|
||||||
|
# Нужно доделать после мержа #935
|
||||||
|
case 6:
|
||||||
|
$info["type"] = "wall_publish";
|
||||||
|
break;
|
||||||
|
# В вк не было такого уведомления, так что unstandart
|
||||||
|
case 7:
|
||||||
|
$info["type"] = "new_posts_in_club";
|
||||||
|
break;
|
||||||
|
# В вк при передаче подарков приходит сообщение, а не уведомление, так что unstandart
|
||||||
|
case 9601:
|
||||||
|
$info["type"] = "sent_gift";
|
||||||
|
$info["parent"] = $this->getModel(1)->toVkApiStruct($this->getModel(1));
|
||||||
|
break;
|
||||||
|
case 9602:
|
||||||
|
$info["type"] = "voices_transfer";
|
||||||
|
$info["parent"] = $this->getModel(1)->toVkApiStruct($this->getModel(1));
|
||||||
|
break;
|
||||||
|
case 9603:
|
||||||
|
$info["type"] = "up_rating";
|
||||||
|
$info["parent"] = $this->getModel(1)->toVkApiStruct($this->getModel(1));
|
||||||
|
$info["parent"]->count = $this->getData();
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
$info["type"] = NULL;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return $info;
|
||||||
|
}
|
||||||
|
|
||||||
|
function toVkApiStruct()
|
||||||
|
{
|
||||||
|
$res = (object)[];
|
||||||
|
|
||||||
|
$info = $this->getVkApiInfo();
|
||||||
|
$res->type = $info["type"];
|
||||||
|
$res->date = $this->getDateTime()->timestamp();
|
||||||
|
$res->parent = $info["parent"];
|
||||||
|
$res->feedback = $info["feedback"];
|
||||||
|
$res->reply = NULL; # Ответы на комментарии не реализованы
|
||||||
|
return $res;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -347,4 +347,20 @@ class Photo extends Media
|
||||||
|
|
||||||
return $photo;
|
return $photo;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function toNotifApiStruct()
|
||||||
|
{
|
||||||
|
$res = (object)[];
|
||||||
|
|
||||||
|
$res->id = $this->getVirtualId();
|
||||||
|
$res->owner_id = $this->getOwner()->getId();
|
||||||
|
$res->aid = 0;
|
||||||
|
$res->src = $this->getURLBySizeId("tiny");
|
||||||
|
$res->src_big = $this->getURLBySizeId("normal");
|
||||||
|
$res->src_small = $this->getURLBySizeId("miniscule");
|
||||||
|
$res->text = $this->getDescription();
|
||||||
|
$res->created = $this->getPublicationTime()->timestamp();
|
||||||
|
|
||||||
|
return $res;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -246,6 +246,23 @@ class Post extends Postable
|
||||||
$this->save();
|
$this->save();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function toNotifApiStruct()
|
||||||
|
{
|
||||||
|
$res = (object)[];
|
||||||
|
|
||||||
|
$res->id = $this->getVirtualId();
|
||||||
|
$res->to_id = $this->getOwner() instanceof Club ? $this->getOwner()->getId() * -1 : $this->getOwner()->getId();
|
||||||
|
$res->from_id = $res->to_id;
|
||||||
|
$res->date = $this->getPublicationTime()->timestamp();
|
||||||
|
$res->text = $this->getText(false);
|
||||||
|
$res->attachments = []; # todo
|
||||||
|
|
||||||
|
$res->copy_owner_id = NULL; # todo
|
||||||
|
$res->copy_post_id = NULL; # todo
|
||||||
|
|
||||||
|
return $res;
|
||||||
|
}
|
||||||
|
|
||||||
function canBeEditedBy(?User $user = NULL): bool
|
function canBeEditedBy(?User $user = NULL): bool
|
||||||
{
|
{
|
||||||
if(!$user)
|
if(!$user)
|
||||||
|
|
|
@ -88,13 +88,14 @@ abstract class Postable extends Attachable
|
||||||
])->group("origin"));
|
])->group("origin"));
|
||||||
}
|
}
|
||||||
|
|
||||||
# TODO add pagination
|
function getLikers(int $page = 1, ?int $perPage = NULL): \Traversable
|
||||||
function getLikers(): \Traversable
|
|
||||||
{
|
{
|
||||||
|
$perPage ??= OPENVK_DEFAULT_PER_PAGE;
|
||||||
|
|
||||||
$sel = DB::i()->getContext()->table("likes")->where([
|
$sel = DB::i()->getContext()->table("likes")->where([
|
||||||
"model" => static::class,
|
"model" => static::class,
|
||||||
"target" => $this->getRecord()->id,
|
"target" => $this->getRecord()->id,
|
||||||
]);
|
])->page($page, $perPage);
|
||||||
|
|
||||||
foreach($sel as $like)
|
foreach($sel as $like)
|
||||||
yield (new Users)->get($like->origin);
|
yield (new Users)->get($like->origin);
|
||||||
|
|
|
@ -219,4 +219,23 @@ class Video extends Media
|
||||||
|
|
||||||
return $video;
|
return $video;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function toNotifApiStruct()
|
||||||
|
{
|
||||||
|
$fromYoutube = $this->getType() == Video::TYPE_EMBED;
|
||||||
|
$res = (object)[];
|
||||||
|
|
||||||
|
$res->id = $this->getVirtualId();
|
||||||
|
$res->owner_id = $this->getOwner()->getId();
|
||||||
|
$res->title = $this->getName();
|
||||||
|
$res->description = $this->getDescription();
|
||||||
|
$res->duration = "22";
|
||||||
|
$res->link = "/video".$this->getOwner()->getId()."_".$this->getVirtualId();
|
||||||
|
$res->image = $this->getThumbnailURL();
|
||||||
|
$res->date = $this->getPublicationTime()->timestamp();
|
||||||
|
$res->views = 0;
|
||||||
|
$res->player = !$fromYoutube ? $this->getURL() : $this->getVideoDriver()->getURL();
|
||||||
|
|
||||||
|
return $res;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -230,6 +230,44 @@ function ovk_is_ssl(): bool
|
||||||
return $GLOBALS["requestIsSSL"];
|
return $GLOBALS["requestIsSSL"];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function parseAttachments(string $attachments)
|
||||||
|
{
|
||||||
|
$attachmentsArr = explode(",", $attachments);
|
||||||
|
$returnArr = [];
|
||||||
|
|
||||||
|
foreach($attachmentsArr as $attachment) {
|
||||||
|
$attachmentType = NULL;
|
||||||
|
|
||||||
|
if(str_contains($attachment, "photo"))
|
||||||
|
$attachmentType = "photo";
|
||||||
|
elseif(str_contains($attachment, "video"))
|
||||||
|
$attachmentType = "video";
|
||||||
|
elseif(str_contains($attachment, "note"))
|
||||||
|
$attachmentType = "note";
|
||||||
|
|
||||||
|
$attachmentIds = str_replace($attachmentType, "", $attachment);
|
||||||
|
$attachmentOwner = (int)explode("_", $attachmentIds)[0];
|
||||||
|
$attachmentId = (int)end(explode("_", $attachmentIds));
|
||||||
|
|
||||||
|
switch($attachmentType) {
|
||||||
|
case "photo":
|
||||||
|
$attachmentObj = (new openvk\Web\Models\Repositories\Photos)->getByOwnerAndVID($attachmentOwner, $attachmentId);
|
||||||
|
$returnArr[] = $attachmentObj;
|
||||||
|
break;
|
||||||
|
case "video":
|
||||||
|
$attachmentObj = (new openvk\Web\Models\Repositories\Videos)->getByOwnerAndVID($attachmentOwner, $attachmentId);
|
||||||
|
$returnArr[] = $attachmentObj;
|
||||||
|
break;
|
||||||
|
case "note":
|
||||||
|
$attachmentObj = (new openvk\Web\Models\Repositories\Notes)->getNoteById($attachmentOwner, $attachmentId);
|
||||||
|
$returnArr[] = $attachmentObj;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return $returnArr;
|
||||||
|
}
|
||||||
|
|
||||||
function ovk_scheme(bool $with_slashes = false): string
|
function ovk_scheme(bool $with_slashes = false): string
|
||||||
{
|
{
|
||||||
$scheme = ovk_is_ssl() ? "https" : "http";
|
$scheme = ovk_is_ssl() ? "https" : "http";
|
||||||
|
|
Loading…
Reference in a new issue