Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
22 commits
Select commit Hold shift + click to select a range
be769f4
Add collectives trash backend provider to files_trashbin
mejo- Apr 12, 2023
cecd019
Trash pages instead of deleting them when files_trashbin is enabled
mejo- May 19, 2023
e8978f4
Allow to restore/delete pages from trash via Collectives API
mejo- May 19, 2023
46874d2
Refactor: move node-related functions from PageService to NodeHelper
mejo- May 19, 2023
88042dd
Add behat tests for page trash
mejo- May 19, 2023
a19e0f7
Remove versions along with pages
mejo- May 22, 2023
d8bb2f7
Delete trash and versions when deleting a collective
mejo- May 22, 2023
8b6ac69
Add behat tests for collectives trash over webdav API
mejo- May 23, 2023
cb18b01
Revert subfolders of parent page when deleting from trash
mejo- May 24, 2023
6300d97
Don't grant access to trash of read-only collectives
mejo- May 24, 2023
bcac981
Restore attachments folder along with page if it exists
mejo- May 24, 2023
c089e16
Restore+remove attachments folder from trash along with page
mejo- May 24, 2023
e310a12
Add behat tests for page trash API in public shares
mejo- May 24, 2023
ea037d5
Add fixes detected by psalm
mejo- May 24, 2023
f935a7c
Call notifyPush when trashing a page also without files_trashbin
mejo- May 25, 2023
b894a77
Delete collective leftovers even if collective folder is already gone
mejo- May 25, 2023
235b4aa
Improve exception message when trashed page not found in database
mejo- May 25, 2023
93c8d63
Also return full PageInfo objects for page trash index
mejo- May 27, 2023
14967ef
Fix handling of deleted pages with subpages
mejo- May 30, 2023
d3a46c4
PageTrashCleanup: Different return values for different failure reasons
mejo- Jun 5, 2023
710a616
Code style fixes by php-cs-fixer
mejo- Jun 5, 2023
34b080a
Make sure long filenames are truncated in trashbin
mejo- Jun 5, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Allow to restore/delete pages from trash via Collectives API
Signed-off-by: Jonas <[email protected]>
  • Loading branch information
mejo- committed Jun 5, 2023
commit e8978f4567d8f001f14db3f6c10a31d8f09d8ece
14 changes: 14 additions & 0 deletions appinfo/routes.php
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,13 @@
['name' => 'page#getAttachments', 'url' => '/_api/{collectiveId}/_pages/parent/{parentId}/page/{id}/attachments',
'verb' => 'GET', 'requirements' => ['collectiveId' => '\d+', 'parentId' => '\d+', 'id' => '\d+']],

// pages trash API
['name' => 'pageTrash#index', 'url' => '/_api/{collectiveId}/_pages/trash', 'verb' => 'GET'],
['name' => 'pageTrash#delete', 'url' => '/_api/{collectiveId}/_pages/trash/{id}', 'verb' => 'DELETE',
'requirements' => ['id' => '\d+']],
['name' => 'pageTrash#restore', 'url' => '/_api/{collectiveId}/_pages/trash/{id}', 'verb' => 'PATCH',
'requirements' => ['id' => '\d+']],

// public collectives API
['name' => 'publicCollective#get', 'url' => '/_api/p/{token}', 'verb' => 'GET'],

Expand All @@ -85,6 +92,13 @@
['name' => 'publicPage#getBacklinks', 'url' => '/_api/p/{token}/_pages/parent/{parentId}/page/{id}/backlinks',
'verb' => 'GET', 'requirements' => ['parentId' => '\d+', 'id' => '\d+']],

// public pages trash API
['name' => 'publicPageTrash#index', 'url' => '/_api/p/{token}/_pages/trash', 'verb' => 'GET'],
['name' => 'publicPageTrash#delete', 'url' => '/_api/p/{token}/_pages/trash/{id}', 'verb' => 'DELETE',
'requirements' => ['id' => '\d+']],
['name' => 'publicPageTrash#restore', 'url' => '/_api/p/{token}/_pages/trash/{id}', 'verb' => 'PATCH',
'requirements' => ['id' => '\d+']],

// default public route (Vue.js frontend)
['name' => 'publicStart#publicIndex', 'url' => '/p/{token}/{path}', 'verb' => 'GET',
'requirements' => ['path' => '.*'], 'defaults' => ['path' => '']],
Expand Down
87 changes: 87 additions & 0 deletions lib/Controller/PageTrashController.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
<?php

namespace OCA\Collectives\Controller;

use OCA\Collectives\Service\PageService;
use OCP\AppFramework\Controller;
use OCP\AppFramework\Http\DataResponse;
use OCP\IRequest;
use OCP\IUserSession;
use Psr\Log\LoggerInterface;

class PageTrashController extends Controller {
private PageService $service;
private IUserSession $userSession;
private LoggerInterface $logger;

use ErrorHelper;

public function __construct(string $appName,
IRequest $request,
PageService $service,
IUserSession $userSession,
LoggerInterface $logger) {
parent::__construct($appName, $request);
$this->service = $service;
$this->userSession = $userSession;
$this->logger = $logger;
}

/**
* @return string
*/
private function getUserId(): string {
return $this->userSession->getUser()->getUID();
}

/**
* @NoAdminRequired
*
* @param int $collectiveId
*
* @return DataResponse
*/
public function index(int $collectiveId): DataResponse {
return $this->handleErrorResponse(function () use ($collectiveId): array {
$userId = $this->getUserId();
$pageInfos = $this->service->findAllTrash($collectiveId, $userId);
return [
"data" => $pageInfos
];
}, $this->logger);
}

/**
* @NoAdminRequired
*
* @param int $collectiveId
* @param int $id
*
* @return DataResponse
*/
public function restore(int $collectiveId, int $id): DataResponse {
return $this->handleErrorResponse(function () use ($collectiveId, $id): array {
$userId = $this->getUserId();
$pageInfo = $this->service->restore($collectiveId, $id, $userId);
return [
"data" => $pageInfo
];
}, $this->logger);
}

/**
* @NoAdminRequired
*
* @param int $collectiveId
* @param int $id
*
* @return DataResponse
*/
public function delete(int $collectiveId, int $id): DataResponse {
return $this->handleErrorResponse(function () use ($collectiveId, $id): array {
$userId = $this->getUserId();
$this->service->delete($collectiveId, $id, $userId);
return [];
}, $this->logger);
}
}
155 changes: 155 additions & 0 deletions lib/Controller/PublicPageTrashController.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,155 @@
<?php

namespace OCA\Collectives\Controller;

use OCA\Collectives\Db\CollectiveShareMapper;
use OCA\Collectives\Model\CollectiveShareInfo;
use OCA\Collectives\Service\CollectiveShareService;
use OCA\Collectives\Service\NotFoundException;
use OCA\Collectives\Service\NotPermittedException;
use OCA\Collectives\Service\PageService;
use OCP\AppFramework\Db\DoesNotExistException;
use OCP\AppFramework\Db\MultipleObjectsReturnedException;
use OCP\AppFramework\Http\DataResponse;
use OCP\AppFramework\PublicShareController;
use OCP\IRequest;
use OCP\ISession;
use Psr\Log\LoggerInterface;

class PublicPageTrashController extends PublicShareController {
private CollectiveShareMapper $collectiveShareMapper;
private CollectiveShareService $collectiveShareService;
private PageService $service;
private LoggerInterface $logger;
private ?CollectiveShareInfo $share = null;

use ErrorHelper;

public function __construct(string $appName,
IRequest $request,
CollectiveShareMapper $collectiveShareMapper,
CollectiveShareService $collectiveShareService,
PageService $service,
ISession $session,
LoggerInterface $logger) {
parent::__construct($appName, $request, $session);
$this->collectiveShareMapper = $collectiveShareMapper;
$this->collectiveShareService = $collectiveShareService;
$this->service = $service;
$this->logger = $logger;
}

/**
* @return string
*/
protected function getPasswordHash(): string {
return '';
}

/**
* @return bool
*/
public function isValidToken(): bool {
try {
$this->collectiveShareMapper->findOneByToken($this->getToken());
} catch (DoesNotExistException | MultipleObjectsReturnedException $e) {
return false;
}

return true;
}

/**
* @return bool
*/
protected function isPasswordProtected(): bool {
return false;
}

/**
* @return CollectiveShareInfo
* @throws NotFoundException
*/
private function getShare(): CollectiveShareInfo {
if (null === $this->share) {
$this->share = $this->collectiveShareService->findShareByToken($this->getToken());

if ($this->share === null) {
throw new NotFoundException('Failed to get shared collective');
}
}

return $this->share;
}

/**
* @return void
* @throws NotFoundException
* @throws NotPermittedException
*/
private function checkEditPermissions(): void {
if (!$this->getShare()->getEditable()) {
throw new NotPermittedException('Not permitted to edit shared collective');
}
}

/**
* @PublicPage
*
* @return DataResponse
*/
public function index(): DataResponse {
return $this->handleErrorResponse(function (): array {
$owner = $this->getShare()->getOwner();
$collectiveId = $this->getShare()->getCollectiveId();
$pageInfos = $this->service->findAll($collectiveId, $owner);
foreach ($pageInfos as $pageInfo) {
// Shares don't have a collective path
$pageInfo->setCollectivePath('');
$pageInfo->setShareToken($this->getToken());
}
return [
"data" => $pageInfos
];
}, $this->logger);
}

/**
* @PublicPage
*
* @param int $id
*
* @return DataResponse
*/
public function restore(int $id): DataResponse {
return $this->handleErrorResponse(function () use ($id): array {
$this->checkEditPermissions();
$owner = $this->getShare()->getOwner();
$collectiveId = $this->getShare()->getCollectiveId();
$pageInfo = $this->service->restore($collectiveId, $id, $owner);
// Shares don't have a collective path
$pageInfo->setCollectivePath('');
$pageInfo->setShareToken($this->getToken());
return [
"data" => $pageInfo
];
}, $this->logger);
}

/**
* @PublicPage
*
* @param int $id
*
* @return DataResponse
*/
public function delete(int $id): DataResponse {
return $this->handleErrorResponse(function () use ($id): array {
$this->checkEditPermissions();
$owner = $this->getShare()->getOwner();
$collectiveId = $this->getShare()->getCollectiveId();
$this->service->delete($collectiveId, $id, $owner);
return [];
}, $this->logger);
}
}
Loading