勾选视频下方的分类,将该视频归类到对应的分类;取消勾选,则将视频从该分类中移除。
+diff --git a/plugins/Common.php b/plugins/Common.php
index 993546a..8bfddec 100644
--- a/plugins/Common.php
+++ b/plugins/Common.php
@@ -14,6 +14,9 @@ Class Common {
' ',
';',
';',
+ '.',
+ '%',
+ ':',
);
return str_replace($findChars, '', $str);
diff --git a/plugins/Html.php b/plugins/Html.php
index fd179c9..67cc5a7 100644
--- a/plugins/Html.php
+++ b/plugins/Html.php
@@ -94,4 +94,29 @@ eof;
return $gacode;
}
+
+ //根据收藏和分类,获取单个收藏视频的所在分类
+ public static function getFavsTags($filename, $tags) {
+ $fileTags = array();
+
+ foreach($tags as $tag_id => $item) {
+ if (in_array($filename, $item['files'])) {
+ array_push($fileTags, $item['name']);
+ }
+ }
+
+ return $fileTags;
+ }
+
+ //获取只包含分类名的数组
+ public static function getTagNames($tags) {
+ $tmp_arr = array();
+
+ foreach ($tags as $id => $tag) {
+ array_push($tmp_arr, $tag['name']);
+ }
+
+ return $tmp_arr;
+ }
+
}
diff --git a/themes/tajian/controller/FrontapiController.php b/themes/tajian/controller/FrontapiController.php
index fb9ab45..7e32fae 100644
--- a/themes/tajian/controller/FrontapiController.php
+++ b/themes/tajian/controller/FrontapiController.php
@@ -158,7 +158,8 @@ Class FrontApiController extends SiteController {
$done = $done && $this->saveBotTask($shareUrl);
if (!empty($tagName)) {
- $done = $done && $this->saveVideoToTag($shareUrl, $tagName);
+ $video_id = $this->getVideoId($shareUrl);
+ $done = $done && $this->saveVideoToTag($video_id, $tagName);
}
//保存任务日志
@@ -189,13 +190,14 @@ Class FrontApiController extends SiteController {
//保存分享视频到tag分类
//TODO: 如果高并发,需要避免数据被覆盖的问题
- protected function saveVideoToTag($url, $tagName) {
+ protected function saveVideoToTag($video_id, $tagName) {
+ if (empty($video_id) || empty($tagName)) {return false;}
+
$tag_dir = __DIR__ . '/../../../www/' . FSC::$app['config']['content_directory'] . FSC::$app['config']['tajian']['tag_dir'];
if (!is_dir($tag_dir)) {
mkdir($tag_dir, 0755, true);
}
- $video_id = $this->getVideoId($url);
$filepath = realpath($tag_dir) . "/{$tagName}.txt";
if (file_exists($filepath)) {
$content = file_get_contents($filepath);
@@ -215,6 +217,35 @@ Class FrontApiController extends SiteController {
}
}
+ //从分类中删除视频
+ protected function deleteVideoFromTag($filename, $tagName) {
+ if (empty($filename) || empty($tagName)) {return false;}
+
+ $tag_dir = __DIR__ . '/../../../www/' . FSC::$app['config']['content_directory'] . FSC::$app['config']['tajian']['tag_dir'];
+ if (!is_dir($tag_dir)) {
+ mkdir($tag_dir, 0755, true);
+ }
+
+ $filepath = realpath($tag_dir) . "/{$tagName}.txt";
+ if (file_exists($filepath)) {
+ $content = file_get_contents($filepath);
+ $videos = explode("\n", $content);
+ $last_id = array_pop($videos);
+ if (!empty($last_id)) {
+ array_push($videos, $last_id);
+ }
+
+ $key = array_search($filename, $videos);
+ if ($key !== false) {
+ unset($videos[$key]);
+ }
+
+ return file_put_contents($filepath, implode("\n", $videos)) !== false;
+ }
+
+ return false;
+ }
+
//保存任务日志
protected function saveTaskLog($url, $title, $tagName) {
$logFile = __DIR__ . '/../../../runtime/' . FSC::$app['config']['tajian']['task_log'];
@@ -327,6 +358,51 @@ eof;
return $done;
}
+ //删除收藏的视频相关的所有文件
+ protected function deleteVideoFiles($filename) {
+ $data_dir = __DIR__ . '/../../../www/' . FSC::$app['config']['content_directory'] . FSC::$app['config']['tajian']['data_dir'];
+ if (!is_dir($data_dir)) {
+ return false;
+ }
+
+ $done = true;
+
+ try {
+ $data_dir = realpath($data_dir);
+
+ //删除.url文件
+ $filepath_url = "{$data_dir}/{$filename}.url";
+ if (file_exists($filepath_url)) {
+ unlink($filepath_url);
+ }
+
+ //删除标题
+ $filepath_title = "{$data_dir}/{$filename}_title.txt";
+ if (file_exists($filepath_title)) {
+ unlink($filepath_title);
+ }
+
+ //删除图片文件
+ $imgTypes = array('jpg', 'jpeg', 'png', 'gif', 'webp');
+ foreach ($imgTypes as $cover_type) {
+ $filepath_cover = "{$data_dir}/{$filename}.{$cover_type}";
+ if (file_exists($filepath_cover)) {
+ unlink($filepath_cover);
+ }
+ }
+
+ //删除图片描述文件
+ $filepath_desc = "{$data_dir}/{$filename}_cover.txt";
+ if (file_exists($filepath_desc)) {
+ unlink($filepath_desc);
+ }
+ }catch(Exception $err) {
+ $done = false;
+ }
+
+ return $done;
+ }
+
//HeroUnion任务数据通知回传接口
/**
* task_id
@@ -785,13 +861,10 @@ eof;
$tags_current = $this->sortTags($menus_sorted, $tags_current);
}
//获取只包含分类名的数组
- $tmp_arr = array();
- foreach ($tags_current as $id => $tag) {
- array_push($tmp_arr, $tag['name']);
- }
+ $allTags = Html::getTagNames($tags_current);
//保存
- $saved = $this->saveTags($tags, $tmp_arr);
+ $saved = $this->saveTags($tags, $allTags);
if (!empty($saved)) {
$msg = "分类已保存";
$code = 1;
@@ -840,6 +913,8 @@ eof;
if (empty($tag_to_delete)) {
$err = "参数错误,缺少tag传参";
+ }else {
+ $tag_to_delete = Common::cleanSpecialChars($tag_to_delete);
}
if (empty($err)) { //如果数据检查通过,尝试保存
@@ -907,28 +982,14 @@ eof;
$scanner->setWebRoot(FSC::$app['config']['content_directory']);
$dirTree = $scanner->scan(__DIR__ . '/../../../www/' . FSC::$app['config']['content_directory'], 3);
- $menus_sorted = array(); //Readme_sort.txt 说明文件内容,一级目录菜单从上到下的排序
- $readmeFile = $scanner->getDefaultReadme();
- if (!empty($readmeFile)) {
- if (!empty($readmeFile['sort'])) {
- $menus_sorted = explode("\n", $readmeFile['sort']);
- }
- }
-
//获取tags分类
$tags_current = $this->getTags($dirTree);
- //排序
- if (!empty($menus_sorted) && !empty($tags_current)) {
- $tags_current = $this->sortTags($menus_sorted, $tags_current);
- }
+
//获取只包含分类名的数组
- $tmp_arr = array();
- foreach ($tags_current as $id => $tag) {
- array_push($tmp_arr, $tag['name']);
- }
-
+ $allTags = Html::getTagNames($tags_current);
+
//最多添加 20 个分类
- if (count($tmp_arr) >= 20) {
+ if (count($allTags) >= 20) {
$err = '最多添加 20 个分类,请合理规划视频分类哦';
}else {
//保存
@@ -946,7 +1007,141 @@ eof;
return $this->renderJson(compact('code', 'msg', 'err'));
}
- //TODO: 视频管理
+ //视频管理:把视频从分类中删除、添加视频到某个分类、删除视频
+ public function actionDeletefav() {
+ $ip = $this->getUserIp();
+ $check_time = 120; //2 分钟内
+ $max_time_in_minutes = 60; //最多 60 次
+
+ $isUserGotRequestLimit = $this->requestLimit($ip, $max_time_in_minutes, $check_time);
+ if ($isUserGotRequestLimit) {
+ $this->logError("Request limit got, ip: {$ip}");
+ throw new Exception('Oops,操作太快了,请喝杯咖啡休息会吧...');
+ }
+
+ //只允许修改自己的数据
+ $loginedUser = Common::getUserFromSession();
+ if (empty($loginedUser['username'])) {
+ throw new Exception('Oops,你还没登录哦');
+ }else if (
+ !empty(FSC::$app['config']['multipleUserUriParse'])
+ && (empty(FSC::$app['user_id']) || FSC::$app['user_id'] != $loginedUser['username'])
+ ) {
+ throw new Exception('Oops,请求地址有误');
+ }
+
+
+ //返回给视图的变量
+ $code = 0;
+ $msg = '';
+ $err = '';
+
+ //用户提交的数据检查
+ $postParams = $this->post();
+ if (!empty($postParams)) {
+ $video_id = $this->post('id', '');
+ $video_filename = $this->post('filename', '');
+
+ if (empty($video_id) || empty($video_filename)) {
+ $err = "参数错误,缺少id和filename传参";
+ }else {
+ $video_id = Common::cleanSpecialChars($video_id);
+ $video_filename = Common::cleanSpecialChars($video_filename);
+ }
+
+ if (empty($err)) { //如果数据检查通过,尝试保存
+ //获取已有的分类
+ $scanner = new DirScanner();
+ $scanner->setWebRoot(FSC::$app['config']['content_directory']);
+ $dirTree = $scanner->scan(__DIR__ . '/../../../www/' . FSC::$app['config']['content_directory'], 3);
+
+ //获取tags分类
+ $tags_current = $this->getTags($dirTree);
+
+ //获取当前视频的所属分类数组
+ $myTags = Html::getFavsTags($video_filename, $tags_current);
+ foreach ($myTags as $item) {
+ $this->deleteVideoFromTag($video_filename, $item); //从分类中删除此视频
+ }
+
+ //删除此视频的所有文件
+ $saved = $this->deleteVideoFiles($video_filename);
+ if (!empty($saved)) {
+ $msg = "视频已删除";
+ $code = 1;
+ }else {
+ $err = '视频删除失败,请稍后重试';
+ }
+ }
+ }
+
+ return $this->renderJson(compact('code', 'msg', 'err'));
+ }
+
+ public function actionUpdatefavstag() {
+ $ip = $this->getUserIp();
+ $check_time = 120; //2 分钟内
+ $max_time_in_minutes = 60; //最多 60 次
+
+ $isUserGotRequestLimit = $this->requestLimit($ip, $max_time_in_minutes, $check_time);
+ if ($isUserGotRequestLimit) {
+ $this->logError("Request limit got, ip: {$ip}");
+ throw new Exception('Oops,操作太快了,请喝杯咖啡休息会吧...');
+ }
+
+ //只允许修改自己的数据
+ $loginedUser = Common::getUserFromSession();
+ if (empty($loginedUser['username'])) {
+ throw new Exception('Oops,你还没登录哦');
+ }else if (
+ !empty(FSC::$app['config']['multipleUserUriParse'])
+ && (empty(FSC::$app['user_id']) || FSC::$app['user_id'] != $loginedUser['username'])
+ ) {
+ throw new Exception('Oops,请求地址有误');
+ }
+
+
+ //返回给视图的变量
+ $code = 0;
+ $msg = '';
+ $err = '';
+
+ //用户提交的数据检查
+ $postParams = $this->post();
+ if (!empty($postParams)) {
+ $video_id = $this->post('id', '');
+ $video_filename = $this->post('filename', '');
+ $tagName = $this->post('tag', '');
+ $action = $this->post('do', 'remove'); //添加:add,移除:remove
+
+ if (empty($video_id) || empty($video_filename) || empty($tagName)) {
+ $err = "参数错误,缺少id、filename、tag传参";
+ }else {
+ $video_id = Common::cleanSpecialChars($video_id);
+ $video_filename = Common::cleanSpecialChars($video_filename);
+ $tagName = Common::cleanSpecialChars($tagName);
+ }
+
+ if (empty($err)) { //如果数据检查通过,尝试保存
+ $saved = false;
+
+ if ($action == 'add') {
+ $saved = $this->saveVideoToTag($video_filename, $tagName); //添加视频到分类
+ }else {
+ $saved = $this->deleteVideoFromTag($video_filename, $tagName); //从分类中删除此视频
+ }
+
+ if ($saved !== false) {
+ $msg = "操作完成";
+ $code = 1;
+ }else {
+ $err = '操作失败,请稍后重试';
+ }
+ }
+ }
+
+ return $this->renderJson(compact('code', 'msg', 'err'));
+ }
}
diff --git a/themes/tajian/controller/MyController.php b/themes/tajian/controller/MyController.php
index 7740163..91561e5 100644
--- a/themes/tajian/controller/MyController.php
+++ b/themes/tajian/controller/MyController.php
@@ -28,6 +28,9 @@ Class MyController extends SiteController {
$dirTree = $scanner->scan(__DIR__ . '/../../../www/' . FSC::$app['config']['content_directory'], 3);
$scanResults = $scanner->getScanResults();
+ //获取目录
+ $menus = $scanner->getMenus();
+
$readmeFile = $scanner->getDefaultReadme();
if (!empty($readmeFile)) {
if (!empty($readmeFile['sort'])) {
@@ -40,6 +43,9 @@ Class MyController extends SiteController {
$htmlReadme = $scanner->fixMDUrls($readmeFile['realpath'], $htmlReadme);
}
+ //默认显示的目录
+ $cateId = $menus[0]['id'];
+
//获取tags分类
$tags = $this->getTags($dirTree);
@@ -53,7 +59,7 @@ Class MyController extends SiteController {
$pageTitle = "{$defaultTitle} | " . FSC::$app['config']['site_name'];
$params = compact(
- 'dirTree', 'scanResults',
+ 'cateId', 'dirTree', 'scanResults',
'htmlReadme', 'tags', 'nickname'
);
return $this->render($viewName, $params, $pageTitle);
@@ -80,4 +86,11 @@ Class MyController extends SiteController {
return $this->actionIndex($viewName, $defaultTitle);
}
+ //管理收藏
+ public function actionFavs() {
+ $defaultTitle = "管理收藏";
+ $viewName = 'favs';
+ return $this->actionIndex($viewName, $defaultTitle);
+ }
+
}
\ No newline at end of file
diff --git a/themes/tajian/controller/SiteController.php b/themes/tajian/controller/SiteController.php
index 825cae6..d46f3d1 100644
--- a/themes/tajian/controller/SiteController.php
+++ b/themes/tajian/controller/SiteController.php
@@ -220,6 +220,8 @@ Class SiteController extends Controller {
//删除分类
protected function deleteTag($tag) {
+ if (empty($tag)) {return false;}
+
$done = false;
try {
diff --git a/themes/tajian/views/my/favs.php b/themes/tajian/views/my/favs.php
new file mode 100644
index 0000000..16b7e0e
--- /dev/null
+++ b/themes/tajian/views/my/favs.php
@@ -0,0 +1,83 @@
+
+
+ 勾选视频下方的分类,将该视频归类到对应的分类;取消勾选,则将视频从该分类中移除。