X-Git-Url: https://git.immae.eu/?a=blobdiff_plain;f=application%2Fapi%2Fcontrollers%2FLinks.php;h=3a9c03553a30fbe5247e48a2a6c30eb4f34e7b51;hb=d2d4f993e1e76bc68b65c48cb18476c404c97a41;hp=01b7e783f0390ce1ff42756507b12cb952791c62;hpb=7f96d9ec21a95cb85d0292b46e18235b20efbcb2;p=github%2Fshaarli%2FShaarli.git diff --git a/application/api/controllers/Links.php b/application/api/controllers/Links.php index 01b7e783..3a9c0355 100644 --- a/application/api/controllers/Links.php +++ b/application/api/controllers/Links.php @@ -4,6 +4,7 @@ namespace Shaarli\Api\Controllers; use Shaarli\Api\ApiUtils; use Shaarli\Api\Exceptions\ApiBadParametersException; +use Shaarli\Api\Exceptions\ApiLinkNotFoundException; use Slim\Http\Request; use Slim\Http\Response; @@ -34,15 +35,14 @@ class Links extends ApiController */ public function getLinks($request, $response) { - $private = $request->getParam('private'); + $private = $request->getParam('visibility'); $links = $this->linkDb->filterSearch( [ 'searchtags' => $request->getParam('searchtags', ''), 'searchterm' => $request->getParam('searchterm', ''), ], false, - // to updated in another PR depending on the API doc - ($private === 'true' || $private === '1') ? 'private' : 'all' + $private ); // Return links from the {offset}th link, starting from 0. @@ -59,10 +59,9 @@ class Links extends ApiController $limit = $request->getParam('limit'); if (empty($limit)) { $limit = self::$DEFAULT_LIMIT; - } - else if (ctype_digit($limit)) { + } elseif (ctype_digit($limit)) { $limit = intval($limit); - } else if ($limit === 'all') { + } elseif ($limit === 'all') { $limit = count($links); } else { throw new ApiBadParametersException('Invalid limit'); @@ -84,4 +83,135 @@ class Links extends ApiController return $response->withJson($out, 200, $this->jsonStyle); } + + /** + * Return a single formatted link by its ID. + * + * @param Request $request Slim request. + * @param Response $response Slim response. + * @param array $args Path parameters. including the ID. + * + * @return Response containing the link array. + * + * @throws ApiLinkNotFoundException generating a 404 error. + */ + public function getLink($request, $response, $args) + { + if (!isset($this->linkDb[$args['id']])) { + throw new ApiLinkNotFoundException(); + } + $index = index_url($this->ci['environment']); + $out = ApiUtils::formatLink($this->linkDb[$args['id']], $index); + + return $response->withJson($out, 200, $this->jsonStyle); + } + + /** + * Creates a new link from posted request body. + * + * @param Request $request Slim request. + * @param Response $response Slim response. + * + * @return Response response. + */ + public function postLink($request, $response) + { + $data = $request->getParsedBody(); + $link = ApiUtils::buildLinkFromRequest($data, $this->conf->get('privacy.default_private_links')); + // duplicate by URL, return 409 Conflict + if (! empty($link['url']) && ! empty($dup = $this->linkDb->getLinkFromUrl($link['url']))) { + return $response->withJson( + ApiUtils::formatLink($dup, index_url($this->ci['environment'])), + 409, + $this->jsonStyle + ); + } + + $link['id'] = $this->linkDb->getNextId(); + $link['shorturl'] = link_small_hash($link['created'], $link['id']); + + // note: general relative URL + if (empty($link['url'])) { + $link['url'] = '?' . $link['shorturl']; + } + + if (empty($link['title'])) { + $link['title'] = $link['url']; + } + + $this->linkDb[$link['id']] = $link; + $this->linkDb->save($this->conf->get('resource.page_cache')); + $this->history->addLink($link); + $out = ApiUtils::formatLink($link, index_url($this->ci['environment'])); + $redirect = $this->ci->router->relativePathFor('getLink', ['id' => $link['id']]); + return $response->withAddedHeader('Location', $redirect) + ->withJson($out, 201, $this->jsonStyle); + } + + /** + * Updates an existing link from posted request body. + * + * @param Request $request Slim request. + * @param Response $response Slim response. + * @param array $args Path parameters. including the ID. + * + * @return Response response. + * + * @throws ApiLinkNotFoundException generating a 404 error. + */ + public function putLink($request, $response, $args) + { + if (! isset($this->linkDb[$args['id']])) { + throw new ApiLinkNotFoundException(); + } + + $index = index_url($this->ci['environment']); + $data = $request->getParsedBody(); + + $requestLink = ApiUtils::buildLinkFromRequest($data, $this->conf->get('privacy.default_private_links')); + // duplicate URL on a different link, return 409 Conflict + if (! empty($requestLink['url']) + && ! empty($dup = $this->linkDb->getLinkFromUrl($requestLink['url'])) + && $dup['id'] != $args['id'] + ) { + return $response->withJson( + ApiUtils::formatLink($dup, $index), + 409, + $this->jsonStyle + ); + } + + $responseLink = $this->linkDb[$args['id']]; + $responseLink = ApiUtils::updateLink($responseLink, $requestLink); + $this->linkDb[$responseLink['id']] = $responseLink; + $this->linkDb->save($this->conf->get('resource.page_cache')); + $this->history->updateLink($responseLink); + + $out = ApiUtils::formatLink($responseLink, $index); + return $response->withJson($out, 200, $this->jsonStyle); + } + + /** + * Delete an existing link by its ID. + * + * @param Request $request Slim request. + * @param Response $response Slim response. + * @param array $args Path parameters. including the ID. + * + * @return Response response. + * + * @throws ApiLinkNotFoundException generating a 404 error. + */ + public function deleteLink($request, $response, $args) + { + if (! isset($this->linkDb[$args['id']])) { + throw new ApiLinkNotFoundException(); + } + $link = $this->linkDb[$args['id']]; + unset($this->linkDb[(int) $args['id']]); + $this->linkDb->save($this->conf->get('resource.page_cache')); + $this->history->deleteLink($link); + + return $response->withStatus(204); + } }