diff options
-rw-r--r-- | application/LinkDB.php | 33 | ||||
-rw-r--r-- | index.php | 50 | ||||
-rw-r--r-- | tests/LinkDBTest.php | 55 |
3 files changed, 102 insertions, 36 deletions
diff --git a/application/LinkDB.php b/application/LinkDB.php index 8ca0fab3..5e38e848 100644 --- a/application/LinkDB.php +++ b/application/LinkDB.php | |||
@@ -464,6 +464,39 @@ You use the community supported version of the original Shaarli project, by Seba | |||
464 | } | 464 | } |
465 | 465 | ||
466 | /** | 466 | /** |
467 | * Rename or delete a tag across all links. | ||
468 | * | ||
469 | * @param string $from Tag to rename | ||
470 | * @param string $to New tag. If none is provided, the from tag will be deleted | ||
471 | * | ||
472 | * @return array|bool List of altered links or false on error | ||
473 | */ | ||
474 | public function renameTag($from, $to) | ||
475 | { | ||
476 | if (empty($from)) { | ||
477 | return false; | ||
478 | } | ||
479 | $delete = empty($to); | ||
480 | // True for case-sensitive tag search. | ||
481 | $linksToAlter = $this->filterSearch(['searchtags' => $from], true); | ||
482 | foreach($linksToAlter as $key => &$value) | ||
483 | { | ||
484 | $tags = preg_split('/\s+/', trim($value['tags'])); | ||
485 | if (($pos = array_search($from, $tags)) !== false) { | ||
486 | if ($delete) { | ||
487 | unset($tags[$pos]); // Remove tag. | ||
488 | } else { | ||
489 | $tags[$pos] = trim($to); | ||
490 | } | ||
491 | $value['tags'] = trim(implode(' ', array_unique($tags))); | ||
492 | $this[$value['id']] = $value; | ||
493 | } | ||
494 | } | ||
495 | |||
496 | return $linksToAlter; | ||
497 | } | ||
498 | |||
499 | /** | ||
467 | * Returns the list of days containing articles (oldest first) | 500 | * Returns the list of days containing articles (oldest first) |
468 | * Output: An array containing days (in format YYYYMMDD). | 501 | * Output: An array containing days (in format YYYYMMDD). |
469 | */ | 502 | */ |
@@ -685,6 +685,7 @@ function showLinkList($PAGE, $LINKSDB, $conf, $pluginManager) { | |||
685 | * @param ConfigManager $conf Configuration Manager instance. | 685 | * @param ConfigManager $conf Configuration Manager instance. |
686 | * @param PluginManager $pluginManager Plugin Manager instance, | 686 | * @param PluginManager $pluginManager Plugin Manager instance, |
687 | * @param LinkDB $LINKSDB | 687 | * @param LinkDB $LINKSDB |
688 | * @param History $history instance | ||
688 | */ | 689 | */ |
689 | function renderPage($conf, $pluginManager, $LINKSDB, $history) | 690 | function renderPage($conf, $pluginManager, $LINKSDB, $history) |
690 | { | 691 | { |
@@ -1176,39 +1177,16 @@ function renderPage($conf, $pluginManager, $LINKSDB, $history) | |||
1176 | die('Wrong token.'); | 1177 | die('Wrong token.'); |
1177 | } | 1178 | } |
1178 | 1179 | ||
1179 | if (isset($_POST['deletetag']) && !empty($_POST['fromtag'])) { | 1180 | $alteredLinks = $LINKSDB->renameTag(escape($_POST['fromtag']), escape($_POST['totag'])); |
1180 | $delete = true; | ||
1181 | } else if (isset($_POST['renametag']) && !empty($_POST['fromtag']) && !empty($_POST['totag'])) { | ||
1182 | $delete = false; | ||
1183 | } else { | ||
1184 | $PAGE->renderPage('changetag'); | ||
1185 | exit; | ||
1186 | } | ||
1187 | |||
1188 | $count = 0; | ||
1189 | $needle = trim($_POST['fromtag']); | ||
1190 | // True for case-sensitive tag search. | ||
1191 | $linksToAlter = $LINKSDB->filterSearch(array('searchtags' => $needle), true); | ||
1192 | foreach($linksToAlter as $key => $value) | ||
1193 | { | ||
1194 | $tags = explode(' ',trim($value['tags'])); | ||
1195 | if (($pos = array_search($needle,$tags)) !== false) { | ||
1196 | if ($delete) { | ||
1197 | unset($tags[$pos]); // Remove tag. | ||
1198 | } else { | ||
1199 | $tags[$pos] = trim($_POST['totag']); | ||
1200 | } | ||
1201 | $value['tags'] = trim(implode(' ', array_unique($tags))); | ||
1202 | $LINKSDB[$key]=$value; | ||
1203 | $history->updateLink($LINKSDB[$key]); | ||
1204 | ++$count; | ||
1205 | } | ||
1206 | } | ||
1207 | $LINKSDB->save($conf->get('resource.page_cache')); | 1181 | $LINKSDB->save($conf->get('resource.page_cache')); |
1182 | foreach ($alteredLinks as $link) { | ||
1183 | $history->updateLink($link); | ||
1184 | } | ||
1185 | $delete = empty($_POST['totag']); | ||
1208 | $redirect = $delete ? 'do=changetag' : 'searchtags='. urlencode(escape($_POST['totag'])); | 1186 | $redirect = $delete ? 'do=changetag' : 'searchtags='. urlencode(escape($_POST['totag'])); |
1209 | $alert = $delete | 1187 | $alert = $delete |
1210 | ? sprintf(t('The tag was removed from %d links.'), $count) | 1188 | ? sprintf(t('The tag was removed from %d links.'), count($alteredLinks)) |
1211 | : sprintf(t('The tag was renamed in %d links.'), $count); | 1189 | : sprintf(t('The tag was renamed in %d links.'), count($alteredLinks)); |
1212 | echo '<script>alert("'. $alert .'");document.location=\'?'. $redirect .'\';</script>'; | 1190 | echo '<script>alert("'. $alert .'");document.location=\'?'. $redirect .'\';</script>'; |
1213 | exit; | 1191 | exit; |
1214 | } | 1192 | } |
@@ -2237,6 +2215,12 @@ if (!isset($_SESSION['LINKS_PER_PAGE'])) { | |||
2237 | $_SESSION['LINKS_PER_PAGE'] = $conf->get('general.links_per_page', 20); | 2215 | $_SESSION['LINKS_PER_PAGE'] = $conf->get('general.links_per_page', 20); |
2238 | } | 2216 | } |
2239 | 2217 | ||
2218 | try { | ||
2219 | $history = new History($conf->get('resource.history')); | ||
2220 | } catch(Exception $e) { | ||
2221 | die($e->getMessage()); | ||
2222 | } | ||
2223 | |||
2240 | $linkDb = new LinkDB( | 2224 | $linkDb = new LinkDB( |
2241 | $conf->get('resource.datastore'), | 2225 | $conf->get('resource.datastore'), |
2242 | isLoggedIn(), | 2226 | isLoggedIn(), |
@@ -2245,12 +2229,6 @@ $linkDb = new LinkDB( | |||
2245 | $conf->get('redirector.encode_url') | 2229 | $conf->get('redirector.encode_url') |
2246 | ); | 2230 | ); |
2247 | 2231 | ||
2248 | try { | ||
2249 | $history = new History($conf->get('resource.history')); | ||
2250 | } catch(Exception $e) { | ||
2251 | die($e->getMessage()); | ||
2252 | } | ||
2253 | |||
2254 | $container = new \Slim\Container(); | 2232 | $container = new \Slim\Container(); |
2255 | $container['conf'] = $conf; | 2233 | $container['conf'] = $conf; |
2256 | $container['plugins'] = $pluginManager; | 2234 | $container['plugins'] = $pluginManager; |
diff --git a/tests/LinkDBTest.php b/tests/LinkDBTest.php index 25438277..5b2f3667 100644 --- a/tests/LinkDBTest.php +++ b/tests/LinkDBTest.php | |||
@@ -487,4 +487,59 @@ class LinkDBTest extends PHPUnit_Framework_TestCase | |||
487 | $this->assertEquals($linkIds[$cpt++], $key); | 487 | $this->assertEquals($linkIds[$cpt++], $key); |
488 | } | 488 | } |
489 | } | 489 | } |
490 | |||
491 | /** | ||
492 | * Test rename tag with a valid value present in multiple links | ||
493 | */ | ||
494 | public function testRenameTagMultiple() | ||
495 | { | ||
496 | self::$refDB->write(self::$testDatastore); | ||
497 | $linkDB = new LinkDB(self::$testDatastore, true, false); | ||
498 | |||
499 | $res = $linkDB->renameTag('cartoon', 'Taz'); | ||
500 | $this->assertEquals(3, count($res)); | ||
501 | $this->assertContains(' Taz ', $linkDB[4]['tags']); | ||
502 | $this->assertContains(' Taz ', $linkDB[1]['tags']); | ||
503 | $this->assertContains(' Taz ', $linkDB[0]['tags']); | ||
504 | } | ||
505 | |||
506 | /** | ||
507 | * Test rename tag with a valid value | ||
508 | */ | ||
509 | public function testRenameTagCaseSensitive() | ||
510 | { | ||
511 | self::$refDB->write(self::$testDatastore); | ||
512 | $linkDB = new LinkDB(self::$testDatastore, true, false, ''); | ||
513 | |||
514 | $res = $linkDB->renameTag('sTuff', 'Taz'); | ||
515 | $this->assertEquals(1, count($res)); | ||
516 | $this->assertEquals('Taz', $linkDB[41]['tags']); | ||
517 | } | ||
518 | |||
519 | /** | ||
520 | * Test rename tag with invalid values | ||
521 | */ | ||
522 | public function testRenameTagInvalid() | ||
523 | { | ||
524 | $linkDB = new LinkDB(self::$testDatastore, false, false); | ||
525 | |||
526 | $this->assertFalse($linkDB->renameTag('', 'test')); | ||
527 | $this->assertFalse($linkDB->renameTag('', '')); | ||
528 | // tag non existent | ||
529 | $this->assertEquals([], $linkDB->renameTag('test', '')); | ||
530 | $this->assertEquals([], $linkDB->renameTag('test', 'retest')); | ||
531 | } | ||
532 | |||
533 | /** | ||
534 | * Test delete tag with a valid value | ||
535 | */ | ||
536 | public function testDeleteTag() | ||
537 | { | ||
538 | self::$refDB->write(self::$testDatastore); | ||
539 | $linkDB = new LinkDB(self::$testDatastore, true, false); | ||
540 | |||
541 | $res = $linkDB->renameTag('cartoon', null); | ||
542 | $this->assertEquals(3, count($res)); | ||
543 | $this->assertNotContains('cartoon', $linkDB[4]['tags']); | ||
544 | } | ||
490 | } | 545 | } |