diff options
Diffstat (limited to 'lib')
25 files changed, 371 insertions, 120 deletions
diff --git a/lib/Command/Fediverse.php b/lib/Command/Fediverse.php index 0a9e7535..e2801bbd 100644 --- a/lib/Command/Fediverse.php +++ b/lib/Command/Fediverse.php @@ -58,8 +58,8 @@ class Fediverse extends Base { parent::configure(); $this->setName('social:fediverse') ->addOption( - 'type', 't', InputArgument::OPTIONAL, - 'Change the type of access management', '' + 'type', 't', InputArgument::OPTIONAL, + 'Change the type of access management', '' ) ->addArgument('action', InputArgument::OPTIONAL, 'add/remove/test address', '') ->addArgument('address', InputArgument::OPTIONAL, 'address/host', '') diff --git a/lib/Command/MigrateAlpha3.php b/lib/Command/MigrateAlpha3.php index e8f9cbac..05774920 100644 --- a/lib/Command/MigrateAlpha3.php +++ b/lib/Command/MigrateAlpha3.php @@ -119,10 +119,10 @@ class MigrateAlpha3 extends Base { $this->setName('social:migrate:alpha3') ->setDescription('Trying to migrate old data to Alpha3') ->addOption( - 'remove-migrated-tables', '', InputOption::VALUE_NONE, 'Remove old table once copy is done' + 'remove-migrated-tables', '', InputOption::VALUE_NONE, 'Remove old table once copy is done' ) ->addOption( - 'force-remove-old-tables', '', InputOption::VALUE_NONE, 'Force remove old tables' + 'force-remove-old-tables', '', InputOption::VALUE_NONE, 'Force remove old tables' ); } diff --git a/lib/Command/NoteCreate.php b/lib/Command/NoteCreate.php index 2aed76e4..d5ea7827 100644 --- a/lib/Command/NoteCreate.php +++ b/lib/Command/NoteCreate.php @@ -96,18 +96,18 @@ class NoteCreate extends Base { parent::configure(); $this->setName('social:note:create') ->addOption( - 'replyTo', 'r', InputOption::VALUE_OPTIONAL, 'in reply to an existing thread' + 'replyTo', 'r', InputOption::VALUE_OPTIONAL, 'in reply to an existing thread' ) ->addOption( - 'to', 't', InputOption::VALUE_OPTIONAL, 'mentioning people' + 'to', 't', InputOption::VALUE_OPTIONAL, 'mentioning people' ) ->addOption( - 'type', 'y', InputOption::VALUE_OPTIONAL, - 'type: public (default), followers, unlisted, direct' + 'type', 'y', InputOption::VALUE_OPTIONAL, + 'type: public (default), followers, unlisted, direct' ) ->addOption( - 'hashtag', 'g', InputOption::VALUE_OPTIONAL, - 'hashtag, without the leading #' + 'hashtag', 'g', InputOption::VALUE_OPTIONAL, + 'hashtag, without the leading #' ) ->addArgument('user_id', InputArgument::REQUIRED, 'userId of the author') ->addArgument('content', InputArgument::REQUIRED, 'content of the post') diff --git a/lib/Command/QueueStatus.php b/lib/Command/QueueStatus.php index 3de1e7ba..2e2bbbc3 100644 --- a/lib/Command/QueueStatus.php +++ b/lib/Command/QueueStatus.php @@ -73,7 +73,7 @@ class QueueStatus extends Base { parent::configure(); $this->setName('social:queue:status') ->addOption( - 'token', 't', InputOption::VALUE_OPTIONAL, 'token of a request' + 'token', 't', InputOption::VALUE_OPTIONAL, 'token of a request' ) ->setDescription('Return status on the request queue'); } diff --git a/lib/Command/Timeline.php b/lib/Command/Timeline.php index b85f91ab..433118c2 100644 --- a/lib/Command/Timeline.php +++ b/lib/Command/Timeline.php @@ -91,6 +91,7 @@ class Timeline extends ExtendedBase { $this->setName('social:stream') ->addArgument('userId', InputArgument::REQUIRED, 'viewer') ->addArgument('timeline', InputArgument::REQUIRED, 'timeline') + ->addOption('local', '', InputOption::VALUE_NONE, 'public') ->addOption('count', '', InputOption::VALUE_REQUIRED, 'number of elements', '5') ->addOption('min_id', '', InputOption::VALUE_REQUIRED, 'min_id', 0) ->addOption('max_id', '', InputOption::VALUE_REQUIRED, 'max_id', 0) @@ -133,10 +134,12 @@ class Timeline extends ExtendedBase { ->setMaxId(intval($input->getOption('max_id'))); try { - $options->setTimeline($input->getArgument('timeline')); + if ($input->getOption('local')) { + $options->setLocal(true); + } + $options->setTimeline($timeline = $input->getArgument('timeline')); $this->outputStreams($this->streamRequest->getTimeline($options)); } catch (UnknownTimelineException $e) { - echo $input->getArgument('timeline'); $this->displayUnsupportedStream($options); } diff --git a/lib/Controller/ApiController.php b/lib/Controller/ApiController.php index a6dc9fba..c089b003 100644 --- a/lib/Controller/ApiController.php +++ b/lib/Controller/ApiController.php @@ -30,7 +30,6 @@ declare(strict_types=1); namespace OCA\Social\Controller; -use OCA\Social\Tools\Traits\TNCDataResponse; use Exception; use OCA\Social\AppInfo\Application; use OCA\Social\Exceptions\AccountDoesNotExistException; @@ -41,19 +40,23 @@ use OCA\Social\Model\ActivityPub\Actor\Person; use OCA\Social\Model\ActivityPub\Stream; use OCA\Social\Model\Client\Options\TimelineOptions; use OCA\Social\Model\Client\SocialClient; +use OCA\Social\Model\Client\Status; +use OCA\Social\Model\Post; use OCA\Social\Service\AccountService; use OCA\Social\Service\CacheActorService; use OCA\Social\Service\ClientService; use OCA\Social\Service\ConfigService; use OCA\Social\Service\FollowService; use OCA\Social\Service\InstanceService; -use OCA\Social\Service\MiscService; +use OCA\Social\Service\PostService; use OCA\Social\Service\StreamService; +use OCA\Social\Tools\Traits\TNCDataResponse; use OCP\AppFramework\Controller; use OCP\AppFramework\Http; use OCP\AppFramework\Http\DataResponse; use OCP\IRequest; use OCP\IUserSession; +use Psr\Log\LoggerInterface; /** * Class ApiController @@ -64,35 +67,45 @@ class ApiController extends Controller { use TNCDataResponse; private IUserSession $userSession; + private LoggerInterface $logger; private InstanceService $instanceService; private ClientService $clientService; private AccountService $accountService; private CacheActorService $cacheActorService; private FollowService $followService; private StreamService $streamService; + private PostService $postService; private ConfigService $configService; - private MiscService $miscService; + private string $bearer = ''; private ?SocialClient $client = null; private ?Person $viewer = null; public function __construct( - IRequest $request, IUserSession $userSession, InstanceService $instanceService, - ClientService $clientService, AccountService $accountService, CacheActorService $cacheActorService, - FollowService $followService, StreamService $streamService, ConfigService $configService, - MiscService $miscService + IRequest $request, + IUserSession $userSession, + LoggerInterface $logger, + InstanceService $instanceService, + ClientService $clientService, + AccountService $accountService, + CacheActorService $cacheActorService, + FollowService $followService, + StreamService $streamService, + PostService $postService, + ConfigService $configService ) { parent::__construct(Application::APP_NAME, $request); $this->userSession = $userSession; + $this->logger = $logger; $this->instanceService = $instanceService; $this->clientService = $clientService; $this->accountService = $accountService; $this->cacheActorService = $cacheActorService; $this->followService = $followService; $this->streamService = $streamService; + $this->postService = $postService; $this->configService = $configService; - $this->miscService = $miscService; $authHeader = trim($this->request->getHeader('Authorization')); if (strpos($authHeader, ' ')) { @@ -212,25 +225,67 @@ class ApiController extends Controller { /** + * @PublicPage + * @NoCSRFRequired + * + * @return DataResponse + */ + public function statusNew(): DataResponse { + try { + $this->initViewer(true); + + $input = file_get_contents('php://input'); + $this->logger->debug('[ApiController] newStatus: ' . $input); + + $status = new Status(); + $status->import($this->convertInput($input)); + + $post = new Post($this->accountService->getActorFromUserId($this->currentSession())); + $post->setContent($status->getStatus()); + $post->setType($status->getVisibility()); + + $activity = $this->postService->createPost($post); + $activity->setExportFormat(ACore::FORMAT_LOCAL); + + return new DataResponse($activity, Http::STATUS_OK); + } catch (Exception $e) { + $this->logger->warning('issues while statusNew', ['exception' => $e]); + + return new DataResponse(['error' => $e->getMessage()], Http::STATUS_BAD_REQUEST); + } + } + + + /** * @NoCSRFRequired * @PublicPage * * @param string $timeline + * @param bool $local * @param int $limit * @param int $max_id * @param int $min_id + * * @return DataResponse */ - public function timelines(string $timeline, int $limit = 20, int $max_id = 0, int $min_id = 0): DataResponse { - $options = new TimelineOptions($this->request); - $options->setFormat(Stream::FORMAT_LOCAL); - $options->setTimeline($timeline); - $options->setLimit($limit); - $options->setMaxId($max_id); - $options->setMinId($min_id); - + public function timelines( + string $timeline, + bool $local = false, + int $limit = 20, + int $max_id = 0, + int $min_id = 0 + ): DataResponse { try { $this->initViewer(true); + + $options = new TimelineOptions($this->request); + $options->setFormat(ACore::FORMAT_LOCAL); + $options->setTimeline($timeline); + $options->setLocal($local); + $options->setLimit($limit); + $options->setMaxId($max_id); + $options->setMinId($min_id); + $posts = $this->streamService->getTimeline($options); return new DataResponse($posts, Http::STATUS_OK); @@ -251,8 +306,8 @@ class ApiController extends Controller { try { $userId = $this->currentSession(); - $this->miscService->log( - '[ApiController] initViewer: ' . $userId . ' (bearer=' . $this->bearer . ')', 0 + $this->logger->debug( + '[ApiController] initViewer: ' . $userId . ' (bearer=' . $this->bearer . ')' ); $account = $this->accountService->getActorFromUserId($userId); @@ -274,6 +329,32 @@ class ApiController extends Controller { } + private function convertInput(string $input): array { + $contentType = $this->request->getHeader('Content-Type'); + + $pos = strpos($contentType, ';'); + if ($pos > 0) { + $contentType = substr($contentType, 0, $pos); + } + + switch ($contentType) { + case 'application/json': + return json_decode($input, true); + + case 'application/x-www-form-urlencoded': + return $this->request->getParams(); + + default: // in case of no header ... + $result = json_decode($input, true); + if (is_array($result)) { + return $result; + } + + return $this->request->getParams(); + } + } + + /** * @return string * @throws AccountDoesNotExistException diff --git a/lib/Controller/OAuthController.php b/lib/Controller/OAuthController.php index 057641e5..744c63ef 100644 --- a/lib/Controller/OAuthController.php +++ b/lib/Controller/OAuthController.php @@ -179,28 +179,28 @@ class OAuthController extends Controller { string $response_type, string $scope = 'read' ): Response { - $user = $this->userSession->getUser(); + $user = $this->userSession->getUser(); - // check actor exists - $this->accountService->getActorFromUserId($user->getUID()); + // check actor exists + $this->accountService->getActorFromUserId($user->getUID()); - if ($response_type !== 'code') { - throw new ClientNotFoundException('invalid response type'); - } + if ($response_type !== 'code') { + throw new ClientNotFoundException('invalid response type'); + } - // check client exists in db - $client = $this->clientService->getFromClientId($client_id); - $this->initialState->provideInitialState('appName', $client->getAppName()); - - return new TemplateResponse(Application::APP_NAME, 'oauth2', [ - 'request' => - [ - 'clientId' => $client_id, - 'redirectUri' => $redirect_uri, - 'responseType' => $response_type, - 'scope' => $scope - ] - ]); + // check client exists in db + $client = $this->clientService->getFromClientId($client_id); + $this->initialState->provideInitialState('appName', $client->getAppName()); + + return new TemplateResponse(Application::APP_NAME, 'oauth2', [ + 'request' => + [ + 'clientId' => $client_id, + 'redirectUri' => $redirect_uri, + 'responseType' => $response_type, + 'scope' => $scope + ] + ]); } diff --git a/lib/Db/ActorsRequest.php b/lib/Db/ActorsRequest.php index 51ff87ad..f0b6178c 100644 --- a/lib/Db/ActorsRequest.php +++ b/lib/Db/ActorsRequest.php @@ -53,13 +53,13 @@ class ActorsRequest extends ActorsRequestBuilder { ->setValue('summary', $qb->createNamedParameter($actor->getSummary())) ->setValue('avatar_version', $qb->createNamedParameter($actor->getAvatarVersion())) ->setValue( - 'preferred_username', $qb->createNamedParameter($actor->getPreferredUsername()) + 'preferred_username', $qb->createNamedParameter($actor->getPreferredUsername()) ) ->setValue('public_key', $qb->createNamedParameter($actor->getPublicKey())) ->setValue('private_key', $qb->createNamedParameter($actor->getPrivateKey())) ->setValue( - 'creation', - $qb->createNamedParameter(new DateTime('now'), IQueryBuilder::PARAM_DATE) + 'creation', + $qb->createNamedParameter(new DateTime('now'), IQueryBuilder::PARAM_DATE) ); $qb->executeStatement(); diff --git a/lib/Db/ActorsRequestBuilder.php b/lib/Db/ActorsRequestBuilder.php index f8aa7e4b..ee6ad7b0 100644 --- a/lib/Db/ActorsRequestBuilder.php +++ b/lib/Db/ActorsRequestBuilder.php @@ -121,7 +121,7 @@ class ActorsRequestBuilder extends CoreRequestBuilder { ->setLocal(true) ->setAvatarVersion($this->getInt('avatar_version', $data, -1)) ->setAccount( - $actor->getPreferredUsername() . '@' . $this->configService->getSocialAddress() + $actor->getPreferredUsername() . '@' . $this->configService->getSocialAddress() ); $actor->setUrlSocial($root) ->setUrl($actor->getId()); diff --git a/lib/Db/CacheActorsRequest.php b/lib/Db/CacheActorsRequest.php index 4903a5f4..0027545d 100644 --- a/lib/Db/CacheActorsRequest.php +++ b/lib/Db/CacheActorsRequest.php @@ -59,7 +59,7 @@ class CacheActorsRequest extends CacheActorsRequestBuilder { ->setValue('featured', $qb->createNamedParameter($actor->getFeatured())) ->setValue('url', $qb->createNamedParameter($actor->getUrl())) ->setValue( - 'preferred_username', $qb->createNamedParameter($actor->getPreferredUsername()) + 'preferred_username', $qb->createNamedParameter($actor->getPreferredUsername()) ) ->setValue('name', $qb->createNamedParameter($actor->getName())) ->setValue('summary', $qb->createNamedParameter($actor->getSummary())) @@ -112,7 +112,7 @@ class CacheActorsRequest extends CacheActorsRequestBuilder { ->set('featured', $qb->createNamedParameter($actor->getFeatured())) ->set('url', $qb->createNamedParameter($actor->getUrl())) ->set( - 'preferred_username', $qb->createNamedParameter($actor->getPreferredUsername()) + 'preferred_username', $qb->createNamedParameter($actor->getPreferredUsername()) ) ->set('name', $qb->createNamedParameter($actor->getName())) ->set('summary', $qb->createNamedParameter($actor->getSummary())) diff --git a/lib/Db/ClientRequest.php b/lib/Db/ClientRequest.php index f6432882..162caada 100644 --- a/lib/Db/ClientRequest.php +++ b/lib/Db/ClientRequest.php @@ -56,7 +56,7 @@ class ClientRequest extends ClientRequestBuilder { $qb->setValue('app_name', $qb->createNamedParameter($client->getAppName())) ->setValue('app_website', $qb->createNamedParameter($client->getAppWebsite())) ->setValue( - 'app_redirect_uris', $qb->createNamedParameter(json_encode($client->getAppRedirectUris())) + 'app_redirect_uris', $qb->createNamedParameter(json_encode($client->getAppRedirectUris())) ) ->setValue('app_client_id', $qb->createNamedParameter($client->getAppClientId())) ->setValue('app_client_secret', $qb->createNamedParameter($client->getAppClientSecret())) diff --git a/lib/Db/CoreRequestBuilder.php b/lib/Db/CoreRequestBuilder.php index 012b0e9a..1b5a73ba 100644 --- a/lib/Db/CoreRequestBuilder.php +++ b/lib/Db/CoreRequestBuilder.php @@ -1054,8 +1054,8 @@ class CoreRequestBuilder { ->selectAlias($prefix . '_f.follow_id', $prefix . '_follow_id') ->selectAlias($prefix . '_f.creation', $prefix . '_creation') ->leftJoin( - $this->defaultSelectAlias, CoreRequestBuilder::TABLE_FOLLOWS, $prefix . '_f', - $andX + $this->defaultSelectAlias, CoreRequestBuilder::TABLE_FOLLOWS, $prefix . '_f', + $andX ); } diff --git a/lib/Db/RequestQueueRequest.php b/lib/Db/RequestQueueRequest.php index 119dd88d..9cb1f908 100644 --- a/lib/Db/RequestQueueRequest.php +++ b/lib/Db/RequestQueueRequest.php @@ -66,9 +66,9 @@ class RequestQueueRequest extends RequestQueueRequestBuilder { ->setValue('author', $qb->createNamedParameter($queue->getAuthor())) ->setValue('activity', $qb->createNamedParameter($queue->getActivity())) ->setValue( - 'instance', $qb->createNamedParameter( - json_encode($queue->getInstance(), JSON_UNESCAPED_SLASHES) - ) + 'instance', $qb->createNamedParameter( + json_encode($queue->getInstance(), JSON_UNESCAPED_SLASHES) + ) ) ->setValue('priority', $qb->createNamedParameter($queue->getPriority())) ->setValue('status', $qb->createNamedParameter($queue->getStatus())) @@ -133,8 +133,8 @@ class RequestQueueRequest extends RequestQueueRequestBuilder { $qb = $this->getRequestQueueUpdateSql(); $qb->set('status', $qb->createNamedParameter(RequestQueue::STATUS_RUNNING)) ->set( - 'last', - $qb->createNamedParameter(new DateTime('now'), IQueryBuilder::PARAM_DATE) + 'last', + $qb->createNamedParameter(new DateTime('now'), IQueryBuilder::PARAM_DATE) ); $this->limitToId($qb, $queue->getId()); $this->limitToStatus($qb, RequestQueue::STATUS_STANDBY); diff --git a/lib/Db/SocialCrossQueryBuilder.php b/lib/Db/SocialCrossQueryBuilder.php index 830d6146..3bc16b12 100644 --- a/lib/Db/SocialCrossQueryBuilder.php +++ b/lib/Db/SocialCrossQueryBuilder.php @@ -183,8 +183,8 @@ class SocialCrossQueryBuilder extends SocialCoreQueryBuilder { ->selectAlias('cd.error', 'cachedocument_error') ->selectAlias('cd.creation', 'cachedocument_creation') ->leftJoin( - $this->getDefaultSelectAlias(), CoreRequestBuilder::TABLE_CACHE_DOCUMENTS, 'cd', - $expr->eq($func->lower($pf . '.' . $fieldDocumentId), $func->lower('cd.id')) + $this->getDefaultSelectAlias(), CoreRequestBuilder::TABLE_CACHE_DOCUMENTS, 'cd', + $expr->eq($func->lower($pf . '.' . $fieldDocumentId), $func->lower('cd.id')) ); } diff --git a/lib/Db/SocialLimitsQueryBuilder.php b/lib/Db/SocialLimitsQueryBuilder.php index 11673466..68c5ae82 100644 --- a/lib/Db/SocialLimitsQueryBuilder.php +++ b/lib/Db/SocialLimitsQueryBuilder.php @@ -313,7 +313,7 @@ class SocialLimitsQueryBuilder extends SocialCrossQueryBuilder { * @param bool $local */ public function limitToLocal(bool $local) { - $this->limitToDBField('local', ($local) ? '1' : '0'); + $this->limitToDBFieldInt('local', ($local) ? 1 : 0); } diff --git a/lib/Db/StreamActionsRequest.php b/lib/Db/StreamActionsRequest.php index c228f7bb..cbea36a0 100644 --- a/lib/Db/StreamActionsRequest.php +++ b/lib/Db/StreamActionsRequest.php @@ -56,9 +56,9 @@ class StreamActionsRequest extends StreamActionsRequestBuilder { ->setValue('stream_id', $qb->createNamedParameter($action->getStreamId())) ->setValue('stream_id_prim', $qb->createNamedParameter($this->prim($action->getStreamId()))) ->setValue( - 'values', $qb->createNamedParameter( - json_encode($values, JSON_UNESCAPED_SLASHES) - ) + 'values', $qb->createNamedParameter( + json_encode($values, JSON_UNESCAPED_SLASHES) + ) ) ->setValue('liked', $qb->createNamedParameter(($liked) ? 1 : 0)) ->setValue('boosted', $qb->createNamedParameter(($boosted) ? 1 : 0)) diff --git a/lib/Db/StreamQueueRequest.php b/lib/Db/StreamQueueRequest.php index 0ad3855e..1bfadf32 100644 --- a/lib/Db/StreamQueueRequest.php +++ b/lib/Db/StreamQueueRequest.php @@ -110,8 +110,8 @@ class StreamQueueRequest extends StreamQueueRequestBuilder { $qb = $this->getStreamQueueUpdateSql(); $qb->set('status', $qb->createNamedParameter(StreamQueue::STATUS_RUNNING)) ->set( - 'last', - $qb->createNamedParameter(new DateTime('now'), IQueryBuilder::PARAM_DATE) + 'last', + $qb->createNamedParameter(new DateTime('now'), IQueryBuilder::PARAM_DATE) ); $this->limitToId($qb, $queue->getId()); $this->limitToStatus($qb, StreamQueue::STATUS_STANDBY); diff --git a/lib/Db/StreamRequest.php b/lib/Db/StreamRequest.php index bf75d21b..813b3e87 100644 --- a/lib/Db/StreamRequest.php +++ b/lib/Db/StreamRequest.php @@ -77,9 +77,9 @@ class StreamRequest extends StreamRequestBuilder { /** @var Note $stream */ $qb->setValue('hashtags', $qb->createNamedParameter(json_encode($stream->getHashtags()))) ->setValue( - 'attachments', $qb->createNamedParameter( - json_encode($stream->getAttachments(), JSON_UNESCAPED_SLASHES) - ) + 'attachments', $qb->createNamedParameter( + json_encode($stream->getAttachments(), JSON_UNESCAPED_SLASHES) + ) ); } @@ -188,15 +188,23 @@ class StreamRequest extends StreamRequestBuilder { /** + * @param string $id + * @param bool $asViewer + * @param int $format + * * @return Stream * @throws StreamNotFoundException */ - public function getStreamById(string $id, bool $asViewer = false): Stream { + public function getStreamById( + string $id, + bool $asViewer = false, + int $format = ACore::FORMAT_ACTIVITYPUB + ): Stream { if ($id === '') { throw new StreamNotFoundException(); }; - $qb = $this->getStreamSelectSql(); + $qb = $this->getStreamSelectSql($format); $qb->limitToIdPrim($qb->prim($id)); $qb->linkToCacheActors('ca', 's.attributed_to_prim'); @@ -340,11 +348,6 @@ class StreamRequest extends StreamRequestBuilder { $result = $this->getTimelineDirect($options); break; case 'public': - $options->setLocal(false); - $result = $this->getTimelinePublic($options); - break; - case 'local': - $options->setLocal(true); $result = $this->getTimelinePublic($options); break; @@ -732,19 +735,19 @@ class StreamRequest extends StreamRequestBuilder { ->setValue('subtype', $qb->createNamedParameter($stream->getSubType())) ->setValue('to', $qb->createNamedParameter($stream->getTo())) ->setValue( - 'to_array', $qb->createNamedParameter( - json_encode($stream->getToArray(), JSON_UNESCAPED_SLASHES) - ) + 'to_array', $qb->createNamedParameter( + json_encode($stream->getToArray(), JSON_UNESCAPED_SLASHES) + ) ) ->setValue( - 'cc', $qb->createNamedParameter( - json_encode($stream->getCcArray(), JSON_UNESCAPED_SLASHES) - ) + 'cc', $qb->createNamedParameter( + json_encode($stream->getCcArray(), JSON_UNESCAPED_SLASHES) + ) ) ->setValue( - 'bcc', $qb->createNamedParameter( - json_encode($stream->getBccArray(), JSON_UNESCAPED_SLASHES) - ) + 'bcc', $qb->createNamedParameter( + json_encode($stream->getBccArray(), JSON_UNESCAPED_SLASHES) + ) ) ->setValue('content', $qb->createNamedParameter($stream->getContent())) ->setValue('summary', $qb->createNamedParameter($stream->getSummary())) @@ -760,13 +763,13 @@ class StreamRequest extends StreamRequestBuilder { ->setValue('details', $qb->createNamedParameter(json_encode($stream->getDetailsAll()))) ->setValue('cache', $qb->createNamedParameter($cache)) ->setValue( - 'filter_duplicate', - $qb->createNamedParameter(($stream->isFilterDuplicate()) ? '1' : '0') + 'filter_duplicate', + $qb->createNamedParameter(($stream->isFilterDuplicate()) |