1
0
mirror of https://gitee.com/koogua/course-tencent-cloud.git synced 2025-08-02 04:42:41 +08:00

Compare commits

..

No commits in common. "master" and "v1.5.1" have entirely different histories.

1438 changed files with 30704 additions and 37862 deletions

3
.gitignore vendored
View File

@ -5,11 +5,12 @@
/config/xs.course.ini /config/xs.course.ini
/config/xs.article.ini /config/xs.article.ini
/config/xs.question.ini /config/xs.question.ini
/config/xs.group.ini
/config/xs.user.ini
/config/alipay/*.crt /config/alipay/*.crt
/config/wxpay/*.pem /config/wxpay/*.pem
/db/migrations/schema.php /db/migrations/schema.php
/public/robots.txt /public/robots.txt
/public/sitemap.xml /public/sitemap.xml
/public/h5 /public/h5
/storage/cache/purifier
*KgTest* *KgTest*

View File

@ -1,329 +1,3 @@
### [v1.7.8](https://gitee.com/koogua/course-tencent-cloud/releases/v1.7.8)(2025-06-20)
- 移除ThrottleLimit
- 增加CloseLiveTask
- 增加搜索页图片alt属性striptags过滤
- 后台增加返回顶部快捷方式
- 前台fixbar增加联系电话
- 优化安装脚本
- 优化课时列表直播提示
- 优化后台返回链接
- 优化统计分析代码位置
- 直播回调后更新课时缓存
- 后台清空头像->上传头像
- sitemap.xml直接写入网站根目录
### [v1.7.7](https://gitee.com/koogua/course-tencent-cloud/releases/v1.7.7)(2025-04-20)
- 优化索引管理工具
- 优化章节等页面UI
- 修正workerman中onMessage问题
- 修正非免费课程试听问题
- 优化layer窗口中的表单跳转
- 文件清理以及命名优化
- 优化倒计时
### [v1.7.6](https://gitee.com/koogua/course-tencent-cloud/releases/v1.7.6)(2025-03-22)
- 升级layui-v2.9.25
- 去除发货中不必要的异常抛出
- 去除文章和问题缓存重建
- 去除多余的文件引用
- 修正每日访问站点积分问题
- 限制全文搜索关键字长度
- 统一规划二维码样式
### [v1.7.5](https://gitee.com/koogua/course-tencent-cloud/releases/v1.7.5)(2025-02-22)
- 优化后台统计图表
- 优化图片放大查看
- 优化错误处理机制
- 优化前台编辑器页面
- 去除一些过度的设计
- 精简属性空判断
- 规整redirect
- 优化bootstrap
- 优化logger
- 优化contact
- 优化logo
- 优化nav
### [v1.7.4](https://gitee.com/koogua/course-tencent-cloud/releases/v1.7.4)(2024-12-10)
- 更新layui-v2.9.20
- 优化编辑器内容自动提交
- 修正课时详情页目录高亮问题
- 修正CommentInfo中点赞判断
- 精简AccountSearchTrait
- 优化kg_h5_index_url()
- 优化CourseUserTrait
- 优化kg_setting()
- 优化CsrfToken
### [v1.7.3](https://gitee.com/koogua/course-tencent-cloud/releases/v1.7.3)(2024-10-10)
- 更新layui-v2.9.16
- 增加编辑器内容自动提交
- 修改文章和提问可用tag数量
- 优化findUserActiveSessions
- 优化findUserActiveTokens
- 优化上传文件失败抛出异常
- 优化默认文件上传
- 优化用户锁定相关
### [v1.7.2](https://gitee.com/koogua/course-tencent-cloud/releases/v1.7.2)(2024-07-31)
- 更新layui-v2.9.14
- 优化docker自动化脚本
- 修正教师直播通知
- 修正课程分类删选问题
- 后台增加客户服务入口
- redis增加expire方法
- 日志记录增加log.trace参数
- 精简代码
### [v1.7.1](https://gitee.com/koogua/course-tencent-cloud/releases/v1.7.1)(2024-06-31)
- 更新layui-v2.9.10
- 更新docker国内镜像地址
- 增加导入镜像构建容器的方式
- 调整微信公众号模板消息
- 移除加载富文本编辑器初始化的语言文件
- 移除consult中多余的chapter_id属性
- 修正课程列表顶部过滤条件区块不能收缩问题
- 用户中心第三方登录列表增加过滤条件
- 后台增加打开/关闭左侧菜单提示
- 优化整理文件mimeType
- iconfont资源本地化
- 优化UploadController
- 优化富文本内容显示样式
- 简化内容图片放大监听
- 去除课程打赏相关内容
- 课程增加能否发布检查
### [v1.7.0](https://gitee.com/koogua/course-tencent-cloud/releases/v1.7.0)(2024-05-15)
- 升级layui-2.9.8
- 调整html编辑器属性
- 增加代码块内容复制
- 清理无用的Captcha配置
- 联系人QQ改为上传二维码图片
- 修正logo,favicon上传路径
- 登录后台同时登录前台
- 移动端修正评论发表
### [v1.6.9](https://gitee.com/koogua/course-tencent-cloud/releases/v1.6.9)(2024-04-15)
- 增加用户删除和还原功能
- 增加unauthorized响应
- 增加post方式传递csrf_token
- 删除chapter中resource_count,consult_count属性
- 精简csrf_token白名单
- 拆解优化migrations创建表脚本
- 修正chapter_user时长重复计数问题
- 修正后台刷新首页缓存问题
- 修正home模块中编辑器图片上传
- 优化文章和提问搜索条件
- 优化课程详情页排版
- 优化storage上传
- 优化CategoryTreeList
- 优化CourseUserTrait
- 更新layui-v2.9.7
### [v1.6.8](https://gitee.com/koogua/course-tencent-cloud/releases/v1.6.8)(2024-01-30)
- 修正course_user中active_time未更新问题
- 修正主页simple模式免费课程模块样式问题
- 修正chapter_user中plan_id=0问题
- 修正课时评论管理链接
- 修正用户active_time搜索条件
- 修正课时发布switch开关
- 精简chapter/lessons.volt
- 去除league/commonmark包
- 去除分类等必选判断
- 更新layui-v2.9.3
- 使用ServiceTrait精简代码
- 优化AccountTrait
- 优化错误处理
### [v1.6.7](https://gitee.com/koogua/course-tencent-cloud/releases/v1.6.7)(2023-12-15)
- 增加文章分类功能
- 增加问题分类功能
- 增加审核等批量功能
- 增加若干业务插件埋点
- 精简重构大量业务逻辑
- 移除秒杀营销功能
- 已发现的问题修复
### [v1.6.6](https://gitee.com/koogua/course-tencent-cloud/releases/v1.6.6)(2023-08-30)
- 还原意外删除的AnswerList.php文件
- 修正邮箱注册提交按钮不可用问题
- 去除删除远程课件逻辑
- 增加课程课件资料总览
- 优化cleanDemoDataTask脚本
- 优化tag表migration脚本
- 命名结构等常规优化
### [v1.6.5](https://gitee.com/koogua/course-tencent-cloud/releases/v1.6.5)(2023-07-15)
- 升级layui-v2.8.8
- 使用本地图像验证码
- 优化计划任务脚本
- 优化日志清理脚本
- 优化钉钉webhook
- 修正图文分享参数问题
### [v1.6.4](https://gitee.com/koogua/course-tencent-cloud/releases/v1.6.4)(2023-06-15)
- 增加推荐课程等Widget
- 更新Composer包
- 修正验证空口令问题
- 优化订单确认页样式
- 优化课程等Me相关信息
- 优化分享URL
- 优化用户课程查找
- 优化通知相关
- 优化Providers
- 优化课程章节权限
- 优化钉钉机器人
### [v1.6.3](https://gitee.com/koogua/course-tencent-cloud/releases/v1.6.3)(2023-05-08)
- 强化文章|提问|课程列表参数检查
- 优化HtmlPurifier内容过滤
- 优化排序条件和分页重复问题
- 优化课程搜索分组条件样式
- 优化课程学习时长同步
- 优化程序语法层面
- 更新Layui-v2.8.2
- 替换ip2region包
- 去除未支付“新鲜”订单检查
- 修正手续费率设置为0无效问题
### [v1.6.2](https://gitee.com/koogua/course-tencent-cloud/releases/v1.6.2)(2023-02-12)
- 增加ServerMonitor监控指标配置
- 同步更新腾讯云短信内容规则
- 文章和问答增加评论开关属性
- 修正视频记忆播放无效问题
- 升级composer包版本
- 优化Repo查询默认排序
- 优化管理后台细节
- 优化二维码输出
- 优化评分检查
### [v1.6.1](https://gitee.com/koogua/course-tencent-cloud/releases/v1.6.1)(2022-12-12)
- 富文本编辑器增加粘贴图片和远程图片本地化
- 修正用户通知标记为已读,计数不归零问题
- 修正播放器中央按钮显示问题
- 优化腾讯云播放地址鉴权参数
- 优化热门作者,答主和问题
- 优化学员学习记录显示
- 优化表单数据提交体验
- 优化单章节层级显示
- 优化ServerInfo类
### [v1.6.0](https://gitee.com/koogua/course-tencent-cloud/releases/v1.6.0)(2022-10-26)
- 播放器中间增加大号播放按钮
- 单页和帮助增加浏览计数属性
- logo上增加首页链接
- 修正分类默认图标问题
- 修正layui-main样式更新带来的问题
- 更新composer包
- 调整退款手续费范围
- 导航部分,教师->师资
- 优化分页组件参数
- 优化内容表格样式
- 优化热门问题和热门答主
- 优化通知计数方式
### [v1.5.9](https://gitee.com/koogua/course-tencent-cloud/releases/v1.5.9)(2022-09-20)
- 修正内容图片上传问题
- 去除user全文索引
- 调整notice目录结构
- 更新默认图片
- 更新直播名格式化
- 更新微博分享链接
- 文章单页等增加SEO关键字
- 专题增加封面上传
- 优化router扫描规则
- 升级layui至v2.7.6
- 增加用户协议和隐私政策
- 优化错误日志
### [v1.5.8](https://gitee.com/koogua/course-tencent-cloud/releases/v1.5.8)(2022-08-28)
- 整理migrations
- 更新自动安装脚本
- 优化登录/注册/忘记密码页
- 修复移动端首页课程缓存刷新
- sitemap条目增加过滤条件
### [v1.5.7](https://gitee.com/koogua/course-tencent-cloud/releases/v1.5.7)(2022-08-18)
- 清理群组残留
- 升级腾讯云存储SDK到v2.5.6
- GuzzleHttp升级到v6.5.7
- 优化HtmlPurifier缓存目录自动创建
- 优化问题回答排序问题
- 优化腾讯云短信错误日志
- 整理查询构建语句
- 整理优化CSS
### [v1.5.6](https://gitee.com/koogua/course-tencent-cloud/releases/v1.5.6)(2022-08-08)
- 增加应用内命令行migrations
- 移除群组和微聊模块
- kindeditor替换vditor
- markdown转html
### [v1.5.5](https://gitee.com/koogua/course-tencent-cloud/releases/v1.5.5)(2022-07-27)
- 修正获分类查询条件
- 修正锁定账户还能登录的问题
- 发货增加noMatchedHandler
- 增加demo数据清理脚本
- 用户课程列表增加角色限定条件
- 精简模块加载和路由扫描
- 优化CsrfToken
- 去除无实质作用的数据表优化
### [v1.5.4](https://gitee.com/koogua/course-tencent-cloud/releases/v1.5.4)(2022-06-15)
- 增加migration助手SettingTrait
- 增加积分兑换会员
- 增加ISP备案和电子执照配置
- 增加获取视频时长补偿机制
- 优化课程和套餐发货
- 优化验证码
- 优化视频点播回调处理任务
- 优化章节排序初始值和步长
- 优化后台视频上传和转码
- 修正获取子分类查询条件
### [v1.5.3](https://gitee.com/koogua/course-tencent-cloud/releases/v1.5.3)(2022-05-30)
- 优化章节排序初始值和步长
- 修复删除群组前台列表仍然显示问题
- 设置360浏览器的默认模式为webkit
- 修复首页简单模式课程项顶部缺少空白
- vditor本地化彻底弃用cdn.jsdelivr.net
- 调整markdown样式
### [v1.5.2](https://gitee.com/koogua/course-tencent-cloud/releases/v1.5.2)(2022-04-17)
- 补充话题列表课程数据结构
- 调整发送验证码相关样式
- 优化套餐和话题下拉课程数据显示
- 去除礼物详情中多出来的"}}"标签
- 修正关闭秒杀订单时没有回填库存的问题
- vditor编辑器切换为七牛cdn加速
### [v1.5.1](https://gitee.com/koogua/course-tencent-cloud/releases/v1.5.1)(2022-03-17) ### [v1.5.1](https://gitee.com/koogua/course-tencent-cloud/releases/v1.5.1)(2022-03-17)
- 推荐课程等列表补充属性 - 推荐课程等列表补充属性

View File

@ -1,23 +1,23 @@
## 酷瓜云课堂 ## 酷瓜云课堂
[![酷瓜云课堂-开源知识付费解决方案](https://portal-1255691183.file.myqcloud.com/img/content/63ec392618bd5.png)](https://www.koogua.com) ![酷瓜云课堂](https://portal-1255691183.file.myqcloud.com/img/content/61dd395c053e5.png)
### 系统介绍 ### 系统介绍
酷瓜云课堂依托腾讯云基础服务架构采用C扩展框架Phalcon开发GPL-2.0开源协议,致力开源网课系统,开源网校系统,开源知识付费系统,开源在线教育系统。 酷瓜云课堂依托腾讯云基础服务架构采用C扩展框架Phalcon开发GPL-2.0开源协议,致力开源网课系统,开源网校系统,开源知识付费系统,开源在线教育系统。
![star](https://www.koogua.com/gitee/badge?user=koogua&project=course-tencent-cloud&type=star) ![star](https://koogua.com/gitee/badge?user=koogua&project=course-tencent-cloud&type=star)
![fork](https://www.koogua.com/gitee/badge?user=koogua&project=course-tencent-cloud&type=fork) ![fork](https://koogua.com/gitee/badge?user=koogua&project=course-tencent-cloud&type=fork)
![license](https://www.koogua.com/gitee/badge?user=koogua&project=course-tencent-cloud&type=license) ![license](https://koogua.com/gitee/badge?user=koogua&project=course-tencent-cloud&type=license)
![release](https://www.koogua.com/gitee/badge?user=koogua&project=course-tencent-cloud&type=release) ![release](https://koogua.com/gitee/badge?user=koogua&project=course-tencent-cloud&type=release)
### 系统功能 ### 系统功能
实现了点播、直播、专栏、问答、会员、积分等。 实现了点播、直播、专栏、面授、问答、会员、群组、微聊、积分、秒杀等。
友情提示: 友情提示:
- 演示系统配置低(2核2G1M 跑多个容器)切莫压测 - 演示系统配置低(1Core1G1M 跑多个容器)切莫压测
- 课程数据来源于网络(无实质内容)切莫购买 - 课程数据来源于网络(无实质内容)切莫购买
- 管理后台已禁止数据提交,私密配置已过滤 - 管理后台已禁止数据提交,私密配置已过滤
@ -34,6 +34,12 @@ H5手机端演示
演示账号13507083515 / 123456 演示账号13507083515 / 123456
微信公众号演示:
![公众号二维码](https://portal-1255691183.file.myqcloud.com/img/content/616f998270eca.png)
演示账号13507083515 / 123456
支付流程演示: 支付流程演示:
- [MySQL提升课程全面讲解MySQL架构设计0.01元)](https://ctc.koogua.com/order/confirm?item_id=1390&item_type=1) - [MySQL提升课程全面讲解MySQL架构设计0.01元)](https://ctc.koogua.com/order/confirm?item_id=1390&item_type=1)
@ -42,25 +48,33 @@ H5手机端演示
Tips: 测试支付请用手机号注册一个新账户,以便接收订单通知,以及避免课程无法购买 Tips: 测试支付请用手机号注册一个新账户,以便接收订单通知,以及避免课程无法购买
即时通讯演示:
请使用以下两个账号在不同终端或者浏览器登录,打开微聊界面
- 帐号A100015@163.com / 123456
- 帐号B100065@163.com / 123456
微信推送演示: 微信推送演示:
Tips: 请用手机注册一个新账号,用户中心 -> 关注订阅,扫码关注公众号。之后的登录、购买、退款、直播、咨询等会有消息推送。 Tips: 请用手机注册一个新账号,用户中心 -> 关注订阅,扫码关注公众号。之后的登录、购买、退款、直播、咨询等会有消息推送。
### 项目组件 ### 项目组件
- 后台框架:[phalcon 3.4](https://phalcon.io) - 后台框架:[phalcon 3.4.5](https://phalcon.io)
- 前端框架:[layui 2.9](https://layui.dev) - 前端框架:[layui 2.6.8](https://layui.com) [layim 3.9.8](https://www.layui.com/layim)(已授权)
- 全文检索:[xunsearch 1.4](http://www.xunsearch.com) - 全文检索:[xunsearch 1.4.9](http://www.xunsearch.com)
- 即时通讯:[workerman 3.5.22](https://workerman.net)
- 基础依赖:[php7.3](https://php.net) [mysql5.7](https://mysql.com) [redis5.0](https://redis.io) - 基础依赖:[php7.3](https://php.net) [mysql5.7](https://mysql.com) [redis5.0](https://redis.io)
### 项目文档 ### 项目文档
- [运行环境搭建](https://www.koogua.com/page/wiki) - [运行环境搭建](https://koogua.com/page/wiki)
- [系统服务配置](https://www.koogua.com/page/wiki) - [系统服务配置](https://koogua.com/page/wiki)
- [客户终端配置](https://www.koogua.com/page/wiki) - [客户终端配置](https://koogua.com/page/wiki)
### 意见反馈 ### 意见反馈
- [码云平台](https://gitee.com/koogua/course-tencent-cloud/issues) - [码云平台](https://gitee.com/koogua/course-tencent-cloud/issues)
- [官方社区](https://www.koogua.com/community) - [官方社区](https://koogua.com/community)
- QQ交流群: 787363898 - QQ交流群: 787363898

View File

@ -8,6 +8,7 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\Question as QuestionRepo; use App\Repos\Question as QuestionRepo;
use App\Repos\User as UserRepo;
class AnswerList extends Builder class AnswerList extends Builder
{ {
@ -17,7 +18,7 @@ class AnswerList extends Builder
$questions = $this->getQuestions($answers); $questions = $this->getQuestions($answers);
foreach ($answers as $key => $answer) { foreach ($answers as $key => $answer) {
$answers[$key]['question'] = $questions[$answer['question_id']] ?? null; $answers[$key]['question'] = $questions[$answer['question_id']] ?? new \stdClass();
} }
return $answers; return $answers;
@ -28,7 +29,7 @@ class AnswerList extends Builder
$users = $this->getUsers($answers); $users = $this->getUsers($answers);
foreach ($answers as $key => $answer) { foreach ($answers as $key => $answer) {
$answers[$key]['owner'] = $users[$answer['owner_id']] ?? null; $answers[$key]['owner'] = $users[$answer['owner_id']] ?? new \stdClass();
} }
return $answers; return $answers;
@ -55,7 +56,20 @@ class AnswerList extends Builder
{ {
$ids = kg_array_column($answers, 'owner_id'); $ids = kg_array_column($answers, 'owner_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -8,6 +8,7 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\Article as ArticleRepo; use App\Repos\Article as ArticleRepo;
use App\Repos\User as UserRepo;
use Phalcon\Text; use Phalcon\Text;
class ArticleFavoriteList extends Builder class ArticleFavoriteList extends Builder
@ -18,7 +19,7 @@ class ArticleFavoriteList extends Builder
$articles = $this->getArticles($relations); $articles = $this->getArticles($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['article'] = $articles[$value['article_id']] ?? null; $relations[$key]['article'] = $articles[$value['article_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -29,7 +30,7 @@ class ArticleFavoriteList extends Builder
$users = $this->getUsers($relations); $users = $this->getUsers($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['user'] = $users[$value['user_id']] ?? null; $relations[$key]['user'] = $users[$value['user_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -69,7 +70,20 @@ class ArticleFavoriteList extends Builder
{ {
$ids = kg_array_column($relations, 'user_id'); $ids = kg_array_column($relations, 'user_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findByIds($ids, ['id', 'name', 'avatar']);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -7,8 +7,9 @@
namespace App\Builders; namespace App\Builders;
use App\Caches\CategoryAllList as CategoryAllListCache; use App\Caches\CategoryList as CategoryListCache;
use App\Models\Category as CategoryModel; use App\Models\Category as CategoryModel;
use App\Repos\User as UserRepo;
class ArticleList extends Builder class ArticleList extends Builder
{ {
@ -27,7 +28,7 @@ class ArticleList extends Builder
$categories = $this->getCategories(); $categories = $this->getCategories();
foreach ($articles as $key => $article) { foreach ($articles as $key => $article) {
$articles[$key]['category'] = $categories[$article['category_id']] ?? null; $articles[$key]['category'] = $categories[$article['category_id']] ?? new \stdClass();
} }
return $articles; return $articles;
@ -38,7 +39,7 @@ class ArticleList extends Builder
$users = $this->getUsers($articles); $users = $this->getUsers($articles);
foreach ($articles as $key => $article) { foreach ($articles as $key => $article) {
$articles[$key]['owner'] = $users[$article['owner_id']] ?? null; $articles[$key]['owner'] = $users[$article['owner_id']] ?? new \stdClass();
} }
return $articles; return $articles;
@ -46,7 +47,7 @@ class ArticleList extends Builder
public function getCategories() public function getCategories()
{ {
$cache = new CategoryAllListCache(); $cache = new CategoryListCache();
$items = $cache->get(CategoryModel::TYPE_ARTICLE); $items = $cache->get(CategoryModel::TYPE_ARTICLE);
@ -68,7 +69,20 @@ class ArticleList extends Builder
{ {
$ids = kg_array_column($articles, 'owner_id'); $ids = kg_array_column($articles, 'owner_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -7,7 +7,6 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\User as UserRepo;
use Phalcon\Di\Injectable; use Phalcon\Di\Injectable;
class Builder extends Injectable class Builder extends Injectable
@ -18,22 +17,4 @@ class Builder extends Injectable
return kg_array_object($items); return kg_array_object($items);
} }
protected function getShallowUserByIds(array $ids)
{
$userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
}
} }

View File

@ -8,16 +8,15 @@
namespace App\Builders; namespace App\Builders;
use App\Models\Category as CategoryModel; use App\Models\Category as CategoryModel;
use App\Repos\Category as CategoryRepo; use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface;
class CategoryTreeList extends Builder class CategoryTreeList extends Builder
{ {
public function handle($type) public function handle($type)
{ {
$categoryRepo = new CategoryRepo(); $topCategories = $this->findTopCategories($type);
$topCategories = $categoryRepo->findTopCategories($type);
if ($topCategories->count() == 0) { if ($topCategories->count() == 0) {
return []; return [];
@ -40,9 +39,7 @@ class CategoryTreeList extends Builder
protected function handleChildren(CategoryModel $category) protected function handleChildren(CategoryModel $category)
{ {
$categoryRepo = new CategoryRepo(); $subCategories = $this->findChildCategories($category->id);
$subCategories = $categoryRepo->findChildCategories($category->id);
if ($subCategories->count() == 0) { if ($subCategories->count() == 0) {
return []; return [];
@ -62,4 +59,37 @@ class CategoryTreeList extends Builder
return $list; return $list;
} }
/**
* @param int $type
* @return ResultsetInterface|Resultset|CategoryModel[]
*/
protected function findTopCategories($type)
{
$query = CategoryModel::query();
$query->where('parent_id = 0');
$query->andWhere('published = 1');
$query->andWhere('deleted = 0');
$query->andWhere('type = :type:', ['type' => $type]);
$query->orderBy('priority ASC');
return $query->execute();
}
/**
* @param int $parentId
* @return ResultsetInterface|Resultset|CategoryModel[]
*/
protected function findChildCategories($parentId)
{
$query = CategoryModel::query();
$query->where('published = 1');
$query->where('deleted = 0');
$query->andWhere('parent_id = :parent_id:', ['parent_id' => $parentId]);
$query->orderBy('priority ASC');
return $query->execute();
}
} }

View File

@ -7,6 +7,8 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\User as UserRepo;
class CommentList extends Builder class CommentList extends Builder
{ {
@ -15,8 +17,8 @@ class CommentList extends Builder
$users = $this->getUsers($comments); $users = $this->getUsers($comments);
foreach ($comments as $key => $comment) { foreach ($comments as $key => $comment) {
$comments[$key]['owner'] = $users[$comment['owner_id']] ?? null; $comments[$key]['owner'] = $users[$comment['owner_id']] ?? new \stdClass();
$comments[$key]['to_user'] = $users[$comment['to_user_id']] ?? null; $comments[$key]['to_user'] = $users[$comment['to_user_id']] ?? new \stdClass();
} }
return $comments; return $comments;
@ -28,7 +30,20 @@ class CommentList extends Builder
$toUserIds = kg_array_column($comments, 'to_user_id'); $toUserIds = kg_array_column($comments, 'to_user_id');
$ids = array_merge($ownerIds, $toUserIds); $ids = array_merge($ownerIds, $toUserIds);
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -7,7 +7,9 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\Chapter as ChapterRepo;
use App\Repos\Course as CourseRepo; use App\Repos\Course as CourseRepo;
use App\Repos\User as UserRepo;
class ConsultList extends Builder class ConsultList extends Builder
{ {
@ -17,7 +19,7 @@ class ConsultList extends Builder
$courses = $this->getCourses($consults); $courses = $this->getCourses($consults);
foreach ($consults as $key => $consult) { foreach ($consults as $key => $consult) {
$consults[$key]['course'] = $courses[$consult['course_id']] ?? null; $consults[$key]['course'] = $courses[$consult['course_id']] ?? new \stdClass();
} }
return $consults; return $consults;
@ -28,8 +30,8 @@ class ConsultList extends Builder
$users = $this->getUsers($consults); $users = $this->getUsers($consults);
foreach ($consults as $key => $consult) { foreach ($consults as $key => $consult) {
$consults[$key]['owner'] = $users[$consult['owner_id']] ?? null; $consults[$key]['owner'] = $users[$consult['owner_id']] ?? new \stdClass();
$consults[$key]['replier'] = $users[$consult['replier_id']] ?? null; $consults[$key]['replier'] = $users[$consult['replier_id']] ?? new \stdClass();
} }
return $consults; return $consults;
@ -52,13 +54,43 @@ class ConsultList extends Builder
return $result; return $result;
} }
public function getChapters(array $consults)
{
$ids = kg_array_column($consults, 'chapter_id');
$chapterRepo = new ChapterRepo();
$chapters = $chapterRepo->findByIds($ids, ['id', 'title']);
$result = [];
foreach ($chapters->toArray() as $chapter) {
$result[$chapter['id']] = $chapter;
}
return $result;
}
public function getUsers(array $consults) public function getUsers(array $consults)
{ {
$ownerIds = kg_array_column($consults, 'owner_id'); $ownerIds = kg_array_column($consults, 'owner_id');
$replierIds = kg_array_column($consults, 'replier_id'); $replierIds = kg_array_column($consults, 'replier_id');
$ids = array_merge($ownerIds, $replierIds); $ids = array_merge($ownerIds, $replierIds);
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -8,6 +8,7 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\Course as CourseRepo; use App\Repos\Course as CourseRepo;
use App\Repos\User as UserRepo;
class CourseFavoriteList extends Builder class CourseFavoriteList extends Builder
{ {
@ -17,7 +18,7 @@ class CourseFavoriteList extends Builder
$courses = $this->getCourses($relations); $courses = $this->getCourses($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['course'] = $courses[$value['course_id']] ?? null; $relations[$key]['course'] = $courses[$value['course_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -28,7 +29,7 @@ class CourseFavoriteList extends Builder
$users = $this->getUsers($relations); $users = $this->getUsers($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['user'] = $users[$value['user_id']] ?? null; $relations[$key]['user'] = $users[$value['user_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -69,7 +70,20 @@ class CourseFavoriteList extends Builder
{ {
$ids = kg_array_column($relations, 'user_id'); $ids = kg_array_column($relations, 'user_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findByIds($ids, ['id', 'name', 'avatar']);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -7,8 +7,9 @@
namespace App\Builders; namespace App\Builders;
use App\Caches\CategoryAllList as CategoryAllListCache; use App\Caches\CategoryList as CategoryListCache;
use App\Models\Category as CategoryModel; use App\Models\Category as CategoryModel;
use App\Repos\User as UserRepo;
class CourseList extends Builder class CourseList extends Builder
{ {
@ -18,7 +19,7 @@ class CourseList extends Builder
$categories = $this->getCategories(); $categories = $this->getCategories();
foreach ($courses as $key => $course) { foreach ($courses as $key => $course) {
$courses[$key]['category'] = $categories[$course['category_id']] ?? null; $courses[$key]['category'] = $categories[$course['category_id']] ?? new \stdClass();
} }
return $courses; return $courses;
@ -29,7 +30,7 @@ class CourseList extends Builder
$teachers = $this->getTeachers($courses); $teachers = $this->getTeachers($courses);
foreach ($courses as $key => $course) { foreach ($courses as $key => $course) {
$courses[$key]['teacher'] = $teachers[$course['teacher_id']] ?? null; $courses[$key]['teacher'] = $teachers[$course['teacher_id']] ?? new \stdClass();
} }
return $courses; return $courses;
@ -37,7 +38,7 @@ class CourseList extends Builder
public function getCategories() public function getCategories()
{ {
$cache = new CategoryAllListCache(); $cache = new CategoryListCache();
$items = $cache->get(CategoryModel::TYPE_COURSE); $items = $cache->get(CategoryModel::TYPE_COURSE);
@ -59,7 +60,20 @@ class CourseList extends Builder
{ {
$ids = kg_array_column($courses, 'teacher_id'); $ids = kg_array_column($courses, 'teacher_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -18,7 +18,7 @@ class CourseTopicList extends Builder
$courses = $this->getCourses($relations); $courses = $this->getCourses($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['course'] = $courses[$value['course_id']] ?? null; $relations[$key]['course'] = $courses[$value['course_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -29,7 +29,7 @@ class CourseTopicList extends Builder
$topics = $this->getTopics($relations); $topics = $this->getTopics($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['topic'] = $topics[$value['topic_id']] ?? null; $relations[$key]['topic'] = $topics[$value['topic_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -45,7 +45,7 @@ class CourseTopicList extends Builder
'id', 'title', 'cover', 'id', 'title', 'cover',
'market_price', 'vip_price', 'market_price', 'vip_price',
'rating', 'model', 'level', 'attrs', 'rating', 'model', 'level', 'attrs',
'user_count', 'lesson_count', 'review_count', 'favorite_count', 'user_count', 'lesson_count',
]; ];
$courses = $courseRepo->findByIds($ids, $columns); $courses = $courseRepo->findByIds($ids, $columns);

View File

@ -8,6 +8,7 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\Course as CourseRepo; use App\Repos\Course as CourseRepo;
use App\Repos\User as UserRepo;
class CourseUserList extends Builder class CourseUserList extends Builder
{ {
@ -17,7 +18,7 @@ class CourseUserList extends Builder
$courses = $this->getCourses($relations); $courses = $this->getCourses($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['course'] = $courses[$value['course_id']] ?? null; $relations[$key]['course'] = $courses[$value['course_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -28,7 +29,7 @@ class CourseUserList extends Builder
$users = $this->getUsers($relations); $users = $this->getUsers($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['user'] = $users[$value['user_id']] ?? null; $relations[$key]['user'] = $users[$value['user_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -73,7 +74,20 @@ class CourseUserList extends Builder
{ {
$ids = kg_array_column($relations, 'user_id'); $ids = kg_array_column($relations, 'user_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findByIds($ids, ['id', 'name', 'avatar']);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

104
app/Builders/DanmuList.php Normal file
View File

@ -0,0 +1,104 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Builders;
use App\Repos\Chapter as ChapterRepo;
use App\Repos\Course as CourseRepo;
use App\Repos\User as UserRepo;
class DanmuList extends Builder
{
public function handleCourses(array $danmus)
{
$courses = $this->getCourses($danmus);
foreach ($danmus as $key => $danmu) {
$danmus[$key]['course'] = $courses[$danmu['course_id']] ?? new \stdClass();
}
return $danmus;
}
public function handleChapters(array $danmus)
{
$chapters = $this->getChapters($danmus);
foreach ($danmus as $key => $danmu) {
$danmus[$key]['chapter'] = $chapters[$danmu['chapter_id']] ?? new \stdClass();
}
return $danmus;
}
public function handleUsers(array $danmus)
{
$users = $this->getUsers($danmus);
foreach ($danmus as $key => $danmu) {
$danmus[$key]['owner'] = $users[$danmu['owner_id']] ?? new \stdClass();
}
return $danmus;
}
public function getCourses(array $danmus)
{
$ids = kg_array_column($danmus, 'course_id');
$courseRepo = new CourseRepo();
$courses = $courseRepo->findByIds($ids, ['id', 'title']);
$result = [];
foreach ($courses->toArray() as $course) {
$result[$course['id']] = $course;
}
return $result;
}
public function getChapters(array $danmus)
{
$ids = kg_array_column($danmus, 'chapter_id');
$chapterRepo = new ChapterRepo();
$chapters = $chapterRepo->findByIds($ids, ['id', 'title']);
$result = [];
foreach ($chapters->toArray() as $chapter) {
$result[$chapter['id']] = $chapter;
}
return $result;
}
public function getUsers(array $danmus)
{
$ids = kg_array_column($danmus, 'owner_id');
$userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
}
}

View File

@ -7,7 +7,7 @@
namespace App\Builders; namespace App\Builders;
use App\Caches\CategoryAllList as CategoryAllListCache; use App\Caches\CategoryList as CategoryListCache;
use App\Models\Category as CategoryModel; use App\Models\Category as CategoryModel;
class HelpList extends Builder class HelpList extends Builder
@ -18,7 +18,7 @@ class HelpList extends Builder
$categories = $this->getCategories(); $categories = $this->getCategories();
foreach ($helps as $key => $help) { foreach ($helps as $key => $help) {
$helps[$key]['category'] = $categories[$help['category_id']] ?? null; $helps[$key]['category'] = $categories[$help['category_id']] ?? new \stdClass();
} }
return $helps; return $helps;
@ -26,7 +26,7 @@ class HelpList extends Builder
public function getCategories() public function getCategories()
{ {
$cache = new CategoryAllListCache(); $cache = new CategoryListCache();
$items = $cache->get(CategoryModel::TYPE_HELP); $items = $cache->get(CategoryModel::TYPE_HELP);

View File

@ -0,0 +1,51 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Builders;
use App\Repos\User as UserRepo;
class ImFriendUserList extends Builder
{
public function handleFriends(array $relations)
{
$users = $this->getFriends($relations);
foreach ($relations as $key => $value) {
$relations[$key]['friend'] = $users[$value['friend_id']] ?? new \stdClass();
}
return $relations;
}
public function getFriends(array $relations)
{
$ids = kg_array_column($relations, 'friend_id');
$userRepo = new UserRepo();
$columns = [
'id', 'name', 'avatar', 'title', 'about', 'vip',
'gender', 'area', 'active_time',
];
$users = $userRepo->findByIds($ids, $columns);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
}
}

View File

@ -0,0 +1,86 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Builders;
use App\Repos\Course as CourseRepo;
use App\Repos\User as UserRepo;
class ImGroupList extends Builder
{
public function handleGroups(array $groups)
{
$baseUrl = kg_cos_url();
foreach ($groups as $key => $group) {
$groups[$key]['avatar'] = $baseUrl . $group['avatar'];
}
return $groups;
}
public function handleCourses(array $groups)
{
$courses = $this->getCourses($groups);
foreach ($groups as $key => $group) {
$groups[$key]['course'] = $courses[$group['course_id']] ?? new \stdClass();
}
return $groups;
}
public function handleUsers(array $groups)
{
$users = $this->getUsers($groups);
foreach ($groups as $key => $group) {
$groups[$key]['owner'] = $users[$group['owner_id']] ?? new \stdClass();
}
return $groups;
}
public function getCourses(array $groups)
{
$ids = kg_array_column($groups, 'course_id');
$courseRepo = new CourseRepo();
$courses = $courseRepo->findByIds($ids, ['id', 'title']);
$result = [];
foreach ($courses->toArray() as $course) {
$result[$course['id']] = $course;
}
return $result;
}
public function getUsers(array $groups)
{
$ids = kg_array_column($groups, 'owner_id');
$userRepo = new UserRepo();
$users = $userRepo->findByIds($ids, ['id', 'name', 'avatar']);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
}
}

View File

@ -0,0 +1,105 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Builders;
use App\Repos\ImGroup as ImGroupRepo;
use App\Repos\User as UserRepo;
class ImGroupUserList extends Builder
{
public function handleGroups(array $relations)
{
$groups = $this->getGroups($relations);
foreach ($relations as $key => $value) {
$relations[$key]['group'] = $groups[$value['group_id']] ?? new \stdClass();
}
return $relations;
}
public function handleUsers(array $relations)
{
$users = $this->getUsers($relations);
foreach ($relations as $key => $value) {
$relations[$key]['user'] = $users[$value['user_id']] ?? new \stdClass();
}
return $relations;
}
public function getUsers(array $relations)
{
$ids = kg_array_column($relations, 'user_id');
$userRepo = new UserRepo();
$columns = ['id', 'name', 'avatar', 'title', 'about', 'vip', 'gender', 'area'];
$users = $userRepo->findByIds($ids, $columns);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
}
public function getGroups(array $relations)
{
$ids = kg_array_column($relations, 'group_id');
$groupRepo = new ImGroupRepo();
$columns = ['id', 'type', 'name', 'avatar', 'about', 'owner_id', 'user_count', 'msg_count'];
$groups = $groupRepo->findByIds($ids, $columns);
$users = $this->getGroupOwners($groups->toArray());
$baseUrl = kg_cos_url();
$result = [];
foreach ($groups->toArray() as $group) {
$group['avatar'] = $baseUrl . $group['avatar'];
$group['owner'] = $users[$group['owner_id']] ?? new \stdClass();
unset($group['owner_id']);
$result[$group['id']] = $group;
}
return $result;
}
protected function getGroupOwners(array $groups)
{
$ids = kg_array_column($groups, 'owner_id');
$userRepo = new UserRepo();
$users = $userRepo->findByIds($ids, ['id', 'name']);
$result = [];
if ($users->count() > 0) {
foreach ($users->toArray() as $user) {
$result[$user['id']] = $user;
}
}
return $result;
}
}

View File

@ -0,0 +1,46 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Builders;
use App\Repos\User as UserRepo;
class ImMessageList extends Builder
{
public function handleSenders(array $messages)
{
$users = $this->getSenders($messages);
foreach ($messages as $key => $message) {
$messages[$key]['sender'] = $users[$message['sender_id']] ?? new \stdClass();
}
return $messages;
}
public function getSenders(array $messages)
{
$ids = kg_array_column($messages, 'sender_id');
$userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
}
}

View File

@ -9,6 +9,7 @@ namespace App\Builders;
use App\Repos\Chapter as ChapterRepo; use App\Repos\Chapter as ChapterRepo;
use App\Repos\Course as CourseRepo; use App\Repos\Course as CourseRepo;
use App\Repos\User as UserRepo;
class LearningList extends Builder class LearningList extends Builder
{ {
@ -18,7 +19,7 @@ class LearningList extends Builder
$courses = $this->getCourses($relations); $courses = $this->getCourses($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['course'] = $courses[$value['course_id']] ?? null; $relations[$key]['course'] = $courses[$value['course_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -29,7 +30,7 @@ class LearningList extends Builder
$chapters = $this->getChapters($relations); $chapters = $this->getChapters($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['chapter'] = $chapters[$value['chapter_id']] ?? null; $relations[$key]['chapter'] = $chapters[$value['chapter_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -40,7 +41,7 @@ class LearningList extends Builder
$users = $this->getUsers($relations); $users = $this->getUsers($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['user'] = $users[$value['user_id']] ?? null; $relations[$key]['user'] = $users[$value['user_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -84,7 +85,17 @@ class LearningList extends Builder
{ {
$ids = kg_array_column($relations, 'user_id'); $ids = kg_array_column($relations, 'user_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findByIds($ids, ['id', 'name']);
$result = [];
foreach ($users->toArray() as $user) {
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -19,7 +19,7 @@ class LiveList extends Builder
$courses = $this->getCourses($lives); $courses = $this->getCourses($lives);
foreach ($lives as $key => $live) { foreach ($lives as $key => $live) {
$lives[$key]['course'] = $courses[$live['course_id']] ?? null; $lives[$key]['course'] = $courses[$live['course_id']] ?? new \stdClass();
} }
return $lives; return $lives;
@ -30,7 +30,7 @@ class LiveList extends Builder
$chapters = $this->getChapters($lives); $chapters = $this->getChapters($lives);
foreach ($lives as $key => $live) { foreach ($lives as $key => $live) {
$lives[$key]['chapter'] = $chapters[$live['chapter_id']] ?? null; $lives[$key]['chapter'] = $chapters[$live['chapter_id']] ?? new \stdClass();
} }
return $lives; return $lives;
@ -63,7 +63,7 @@ class LiveList extends Builder
foreach ($courses->toArray() as $course) { foreach ($courses->toArray() as $course) {
$course['cover'] = $baseUrl . $course['cover']; $course['cover'] = $baseUrl . $course['cover'];
$course['teacher'] = $teachers[$course['teacher_id']] ?? null; $course['teacher'] = $teachers[$course['teacher_id']] ?? new \stdClass();
$result[$course['id']] = [ $result[$course['id']] = [
'id' => $course['id'], 'id' => $course['id'],
'title' => $course['title'], 'title' => $course['title'],

View File

@ -7,6 +7,8 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\User as UserRepo;
class NotificationList extends Builder class NotificationList extends Builder
{ {
@ -15,8 +17,8 @@ class NotificationList extends Builder
$users = $this->getUsers($notifications); $users = $this->getUsers($notifications);
foreach ($notifications as $key => $notification) { foreach ($notifications as $key => $notification) {
$notifications[$key]['sender'] = $users[$notification['sender_id']] ?? null; $notifications[$key]['sender'] = $users[$notification['sender_id']] ?? new \stdClass();
$notifications[$key]['receiver'] = $users[$notification['receiver_id']] ?? null; $notifications[$key]['receiver'] = $users[$notification['receiver_id']] ?? new \stdClass();
} }
return $notifications; return $notifications;
@ -28,7 +30,20 @@ class NotificationList extends Builder
$receiverIds = kg_array_column($notifications, 'receiver_id'); $receiverIds = kg_array_column($notifications, 'receiver_id');
$ids = array_merge($senderIds, $receiverIds); $ids = array_merge($senderIds, $receiverIds);
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -9,6 +9,7 @@ namespace App\Builders;
use App\Models\Course as CourseModel; use App\Models\Course as CourseModel;
use App\Models\Order as OrderModel; use App\Models\Order as OrderModel;
use App\Repos\User as UserRepo;
class OrderList extends Builder class OrderList extends Builder
{ {
@ -29,7 +30,7 @@ class OrderList extends Builder
$users = $this->getUsers($orders); $users = $this->getUsers($orders);
foreach ($orders as $key => $order) { foreach ($orders as $key => $order) {
$orders[$key]['owner'] = $users[$order['owner_id']] ?? null; $orders[$key]['owner'] = $users[$order['owner_id']] ?? new \stdClass();
} }
return $orders; return $orders;
@ -112,13 +113,8 @@ class OrderList extends Builder
$me['allow_refund'] = $refundStatusOk && $refundTimeOk ? 1 : 0; $me['allow_refund'] = $refundStatusOk && $refundTimeOk ? 1 : 0;
} }
if ($payStatusOk == 1) { $me['allow_pay'] = $payStatusOk;
$me['allow_pay'] = 1; $me['allow_cancel'] = $cancelStatusOk;
}
if ($cancelStatusOk == 1) {
$me['allow_cancel'] = 1;
}
return $me; return $me;
} }
@ -153,6 +149,20 @@ class OrderList extends Builder
return $itemInfo; return $itemInfo;
} }
/**
* @param string $itemInfo
* @return mixed
*/
protected function handleRewardInfo($itemInfo)
{
if (!empty($itemInfo) && is_string($itemInfo)) {
$itemInfo = json_decode($itemInfo, true);
$itemInfo['course']['cover'] = $this->imgBaseUrl . $itemInfo['course']['cover'];
}
return $itemInfo;
}
/** /**
* @param string $itemInfo * @param string $itemInfo
* @return mixed * @return mixed
@ -174,7 +184,17 @@ class OrderList extends Builder
{ {
$ids = kg_array_column($orders, 'owner_id'); $ids = kg_array_column($orders, 'owner_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$result = [];
foreach ($users->toArray() as $user) {
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -8,6 +8,7 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\Question as QuestionRepo; use App\Repos\Question as QuestionRepo;
use App\Repos\User as UserRepo;
use Phalcon\Text; use Phalcon\Text;
class QuestionFavoriteList extends Builder class QuestionFavoriteList extends Builder
@ -18,7 +19,7 @@ class QuestionFavoriteList extends Builder
$questions = $this->getQuestions($relations); $questions = $this->getQuestions($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['question'] = $questions[$value['question_id']] ?? null; $relations[$key]['question'] = $questions[$value['question_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -29,7 +30,7 @@ class QuestionFavoriteList extends Builder
$users = $this->getUsers($relations); $users = $this->getUsers($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['user'] = $users[$value['user_id']] ?? null; $relations[$key]['user'] = $users[$value['user_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -69,7 +70,20 @@ class QuestionFavoriteList extends Builder
{ {
$ids = kg_array_column($relations, 'user_id'); $ids = kg_array_column($relations, 'user_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -7,8 +7,9 @@
namespace App\Builders; namespace App\Builders;
use App\Caches\CategoryAllList as CategoryAllListCache; use App\Caches\CategoryList as CategoryListCache;
use App\Models\Category as CategoryModel; use App\Models\Category as CategoryModel;
use App\Repos\User as UserRepo;
class QuestionList extends Builder class QuestionList extends Builder
{ {
@ -22,15 +23,15 @@ class QuestionList extends Builder
return $questions; return $questions;
} }
public function handleCategories(array $questions) public function handleCategories(array $articles)
{ {
$categories = $this->getCategories(); $categories = $this->getCategories();
foreach ($questions as $key => $question) { foreach ($articles as $key => $article) {
$questions[$key]['category'] = $categories[$question['category_id']] ?? null; $articles[$key]['category'] = $categories[$article['category_id']] ?? new \stdClass();
} }
return $questions; return $articles;
} }
public function handleUsers(array $questions) public function handleUsers(array $questions)
@ -38,8 +39,8 @@ class QuestionList extends Builder
$users = $this->getUsers($questions); $users = $this->getUsers($questions);
foreach ($questions as $key => $question) { foreach ($questions as $key => $question) {
$questions[$key]['owner'] = $users[$question['owner_id']] ?? null; $questions[$key]['owner'] = $users[$question['owner_id']] ?? new \stdClass();
$questions[$key]['last_replier'] = $users[$question['last_replier_id']] ?? null; $questions[$key]['last_replier'] = $users[$question['last_replier_id']] ?? new \stdClass();
} }
return $questions; return $questions;
@ -47,7 +48,7 @@ class QuestionList extends Builder
public function getCategories() public function getCategories()
{ {
$cache = new CategoryAllListCache(); $cache = new CategoryListCache();
$items = $cache->get(CategoryModel::TYPE_QUESTION); $items = $cache->get(CategoryModel::TYPE_QUESTION);
@ -71,7 +72,20 @@ class QuestionList extends Builder
$lastReplierIds = kg_array_column($questions, 'last_replier_id'); $lastReplierIds = kg_array_column($questions, 'last_replier_id');
$ids = array_merge($ownerIds, $lastReplierIds); $ids = array_merge($ownerIds, $lastReplierIds);
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -9,6 +9,7 @@ namespace App\Builders;
use App\Models\Refund as RefundModel; use App\Models\Refund as RefundModel;
use App\Repos\Order as OrderRepo; use App\Repos\Order as OrderRepo;
use App\Repos\User as UserRepo;
class RefundList extends Builder class RefundList extends Builder
{ {
@ -18,7 +19,7 @@ class RefundList extends Builder
$orders = $this->getOrders($trades); $orders = $this->getOrders($trades);
foreach ($trades as $key => $trade) { foreach ($trades as $key => $trade) {
$trades[$key]['order'] = $orders[$trade['order_id']] ?? null; $trades[$key]['order'] = $orders[$trade['order_id']] ?? new \stdClass();
} }
return $trades; return $trades;
@ -29,7 +30,7 @@ class RefundList extends Builder
$users = $this->getUsers($refunds); $users = $this->getUsers($refunds);
foreach ($refunds as $key => $refund) { foreach ($refunds as $key => $refund) {
$refunds[$key]['owner'] = $users[$refund['owner_id']] ?? null; $refunds[$key]['owner'] = $users[$refund['owner_id']] ?? new \stdClass();
} }
return $refunds; return $refunds;
@ -74,7 +75,20 @@ class RefundList extends Builder
{ {
$ids = kg_array_column($refunds, 'owner_id'); $ids = kg_array_column($refunds, 'owner_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -7,6 +7,8 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\User as UserRepo;
class ReportList extends Builder class ReportList extends Builder
{ {
@ -15,7 +17,7 @@ class ReportList extends Builder
$users = $this->getUsers($reports); $users = $this->getUsers($reports);
foreach ($reports as $key => $report) { foreach ($reports as $key => $report) {
$reports[$key]['owner'] = $users[$report['owner_id']] ?? null; $reports[$key]['owner'] = $users[$report['owner_id']] ?? new \stdClass();
} }
return $reports; return $reports;
@ -25,7 +27,20 @@ class ReportList extends Builder
{ {
$ids = kg_array_column($reports, 'owner_id'); $ids = kg_array_column($reports, 'owner_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -17,7 +17,7 @@ class ResourceList extends Builder
$uploads = $this->getUploads($relations); $uploads = $this->getUploads($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['upload'] = $uploads[$value['upload_id']] ?? null; $relations[$key]['upload'] = $uploads[$value['upload_id']] ?? new \stdClass();
} }
return $relations; return $relations;

View File

@ -8,6 +8,7 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\Course as CourseRepo; use App\Repos\Course as CourseRepo;
use App\Repos\User as UserRepo;
class ReviewList extends Builder class ReviewList extends Builder
{ {
@ -17,7 +18,7 @@ class ReviewList extends Builder
$courses = $this->getCourses($reviews); $courses = $this->getCourses($reviews);
foreach ($reviews as $key => $review) { foreach ($reviews as $key => $review) {
$reviews[$key]['course'] = $courses[$review['course_id']] ?? null; $reviews[$key]['course'] = $courses[$review['course_id']] ?? new \stdClass();
} }
return $reviews; return $reviews;
@ -28,7 +29,7 @@ class ReviewList extends Builder
$users = $this->getUsers($reviews); $users = $this->getUsers($reviews);
foreach ($reviews as $key => $review) { foreach ($reviews as $key => $review) {
$reviews[$key]['owner'] = $users[$review['owner_id']] ?? null; $reviews[$key]['owner'] = $users[$review['owner_id']] ?? new \stdClass();
} }
return $reviews; return $reviews;
@ -55,7 +56,20 @@ class ReviewList extends Builder
{ {
$ids = kg_array_column($reviews, 'owner_id'); $ids = kg_array_column($reviews, 'owner_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -8,6 +8,7 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\Tag as TagRepo; use App\Repos\Tag as TagRepo;
use App\Repos\User as UserRepo;
class TagFollowList extends Builder class TagFollowList extends Builder
{ {
@ -17,7 +18,7 @@ class TagFollowList extends Builder
$tags = $this->getTags($relations); $tags = $this->getTags($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['tag'] = $tags[$value['tag_id']] ?? null; $relations[$key]['tag'] = $tags[$value['tag_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -28,7 +29,7 @@ class TagFollowList extends Builder
$users = $this->getUsers($relations); $users = $this->getUsers($relations);
foreach ($relations as $key => $value) { foreach ($relations as $key => $value) {
$relations[$key]['user'] = $users[$value['user_id']] ?? null; $relations[$key]['user'] = $users[$value['user_id']] ?? new \stdClass();
} }
return $relations; return $relations;
@ -60,7 +61,20 @@ class TagFollowList extends Builder
{ {
$ids = kg_array_column($relations, 'user_id'); $ids = kg_array_column($relations, 'user_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findByIds($ids, ['id', 'name', 'avatar']);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -8,6 +8,7 @@
namespace App\Builders; namespace App\Builders;
use App\Repos\Order as OrderRepo; use App\Repos\Order as OrderRepo;
use App\Repos\User as UserRepo;
class TradeList extends Builder class TradeList extends Builder
{ {
@ -17,7 +18,7 @@ class TradeList extends Builder
$orders = $this->getOrders($trades); $orders = $this->getOrders($trades);
foreach ($trades as $key => $trade) { foreach ($trades as $key => $trade) {
$trades[$key]['order'] = $orders[$trade['order_id']] ?? null; $trades[$key]['order'] = $orders[$trade['order_id']] ?? new \stdClass();
} }
return $trades; return $trades;
@ -28,7 +29,7 @@ class TradeList extends Builder
$users = $this->getUsers($trades); $users = $this->getUsers($trades);
foreach ($trades as $key => $trade) { foreach ($trades as $key => $trade) {
$trades[$key]['owner'] = $users[$trade['owner_id']] ?? null; $trades[$key]['owner'] = $users[$trade['owner_id']] ?? new \stdClass();
} }
return $trades; return $trades;
@ -55,7 +56,20 @@ class TradeList extends Builder
{ {
$ids = kg_array_column($trades, 'owner_id'); $ids = kg_array_column($trades, 'owner_id');
return $this->getShallowUserByIds($ids); $userRepo = new UserRepo();
$users = $userRepo->findShallowUserByIds($ids);
$baseUrl = kg_cos_url();
$result = [];
foreach ($users->toArray() as $user) {
$user['avatar'] = $baseUrl . $user['avatar'];
$result[$user['id']] = $user;
}
return $result;
} }
} }

View File

@ -8,7 +8,6 @@
namespace App\Builders; namespace App\Builders;
use App\Models\User as UserModel; use App\Models\User as UserModel;
use App\Repos\Account as AccountRepo;
use App\Repos\Role as RoleRepo; use App\Repos\Role as RoleRepo;
class UserList extends Builder class UserList extends Builder
@ -25,17 +24,6 @@ class UserList extends Builder
return $users; return $users;
} }
public function handleAccounts(array $users)
{
$accounts = $this->getAccounts($users);
foreach ($users as $key => $user) {
$users[$key]['account'] = $accounts[$user['id']] ?? null;
}
return $users;
}
public function handleAdminRoles(array $users) public function handleAdminRoles(array $users)
{ {
$roles = $this->getAdminRoles($users); $roles = $this->getAdminRoles($users);
@ -58,26 +46,6 @@ class UserList extends Builder
return $users; return $users;
} }
protected function getAccounts(array $users)
{
$ids = kg_array_column($users, 'id');
$accountRepo = new AccountRepo();
$accounts = $accountRepo->findByIds($ids);
$result = [];
foreach ($accounts as $account) {
$result[$account->id] = [
'phone' => $account->phone,
'email' => $account->email,
];
}
return $result;
}
protected function getAdminRoles(array $users) protected function getAdminRoles(array $users)
{ {
$ids = kg_array_column($users, 'admin_role'); $ids = kg_array_column($users, 'admin_role');

View File

@ -27,10 +27,10 @@ class AppInfo extends Cache
$appInfo = new \App\Library\AppInfo(); $appInfo = new \App\Library\AppInfo();
return [ return [
'name' => $appInfo->get('name'), 'name' => $appInfo->name,
'alias' => $appInfo->get('alias'), 'alias' => $appInfo->alias,
'link' => $appInfo->get('link'), 'link' => $appInfo->link,
'version' => $appInfo->get('version'), 'version' => $appInfo->version,
]; ];
} }

36
app/Caches/Article.php Normal file
View File

@ -0,0 +1,36 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Repos\Article as ArticleRepo;
class Article extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "article:{$id}";
}
public function getContent($id = null)
{
$articleRepo = new ArticleRepo();
$article = $articleRepo->findById($id);
return $article ?: null;
}
}

View File

@ -1,46 +0,0 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Category as CategoryModel;
use Phalcon\Mvc\Model\Resultset;
class CategoryAllList extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "category_all_list:{$id}";
}
public function getContent($id = null)
{
/**
* @var Resultset $categories
*/
$categories = CategoryModel::query()
->columns(['id', 'parent_id', 'name', 'priority', 'level', 'path'])
->where('type = :type:', ['type' => $id])
->orderBy('level ASC, priority ASC')
->execute();
if ($categories->count() == 0) {
return [];
}
return $categories->toArray();
}
}

View File

@ -20,19 +20,23 @@ class CategoryList extends Cache
return $this->lifetime; return $this->lifetime;
} }
public function getKey($id = null) public function getKey($type = null)
{ {
return "category_list:{$id}"; return "category_list:{$type}";
} }
public function getContent($id = null) /**
* @param null $type
* @return array
*/
public function getContent($type = null)
{ {
/** /**
* @var Resultset $categories * @var Resultset $categories
*/ */
$categories = CategoryModel::query() $categories = CategoryModel::query()
->columns(['id', 'parent_id', 'name', 'priority', 'level', 'path']) ->columns(['id', 'parent_id', 'name', 'priority', 'level', 'path'])
->where('type = :type:', ['type' => $id]) ->where('type = :type:', ['type' => $type])
->andWhere('published = 1') ->andWhere('published = 1')
->andWhere('deleted = 0') ->andWhere('deleted = 0')
->orderBy('level ASC, priority ASC') ->orderBy('level ASC, priority ASC')

View File

@ -19,16 +19,16 @@ class CategoryTreeList extends Cache
return $this->lifetime; return $this->lifetime;
} }
public function getKey($id = null) public function getKey($type = null)
{ {
return "category_tree_list:{$id}"; return "category_tree_list:{$type}";
} }
public function getContent($id = null) public function getContent($type = null)
{ {
$builder = new CategoryTreeListBuilder(); $builder = new CategoryTreeListBuilder();
$list = $builder->handle($id); $list = $builder->handle($type);
return $list ?: []; return $list ?: [];
} }

View File

@ -12,7 +12,7 @@ use App\Repos\Chapter as ChapterRepo;
class Chapter extends Cache class Chapter extends Cache
{ {
protected $lifetime = 86400; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -9,7 +9,6 @@ namespace App\Caches;
use App\Library\Cache\Backend\Redis as RedisCache; use App\Library\Cache\Backend\Redis as RedisCache;
use Phalcon\Di\Injectable; use Phalcon\Di\Injectable;
use Redis;
abstract class Counter extends Injectable abstract class Counter extends Injectable
{ {
@ -20,7 +19,7 @@ abstract class Counter extends Injectable
protected $cache; protected $cache;
/** /**
* @var Redis * @var \Redis
*/ */
protected $redis; protected $redis;
@ -31,13 +30,19 @@ abstract class Counter extends Injectable
$this->redis = $this->cache->getRedis(); $this->redis = $this->cache->getRedis();
} }
/**
* 获取缓存内容
*
* @param mixed $id
* @return array
*/
public function get($id = null) public function get($id = null)
{ {
$key = $this->getKey($id); $key = $this->getKey($id);
$content = $this->redis->hGetAll($key); $content = $this->redis->hGetAll($key);
if (!$this->redis->exists($key)) { if (!$this->cache->exists($key)) {
$content = $this->getContent($id); $content = $this->getContent($id);
$lifetime = $this->getLifetime(); $lifetime = $this->getLifetime();
@ -49,13 +54,23 @@ abstract class Counter extends Injectable
return $content; return $content;
} }
/**
* 删除缓存内容
*
* @param mixed $id
*/
public function delete($id = null) public function delete($id = null)
{ {
$key = $this->getKey($id); $key = $this->getKey($id);
$this->redis->del($key); $this->cache->delete($key);
} }
/**
* 重建缓存内容
*
* @param mixed $id
*/
public function rebuild($id = null) public function rebuild($id = null)
{ {
$this->delete($id); $this->delete($id);

View File

@ -12,7 +12,7 @@ use App\Repos\Course as CourseRepo;
class Course extends Cache class Course extends Cache
{ {
protected $lifetime = 86400; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -0,0 +1,59 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Category as CategoryModel;
use App\Repos\Course as CourseRepo;
class CourseCategoryList extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "course_category_list:{$id}";
}
public function getContent($id = null)
{
$courseRepo = new CourseRepo();
$categories = $courseRepo->findCategories($id);
if ($categories->count() == 0) {
return [];
}
return $this->handleContent($categories);
}
/**
* @param CategoryModel[] $categories
* @return array
*/
public function handleContent($categories)
{
$result = [];
foreach ($categories as $category) {
$result[] = [
'id' => $category->id,
'name' => $category->name,
];
}
return $result;
}
}

View File

@ -13,7 +13,7 @@ use App\Repos\Course as CourseRepo;
class CoursePackageList extends Cache class CoursePackageList extends Cache
{ {
protected $lifetime = 86400; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -1,6 +1,6 @@
<?php <?php
/** /**
* @copyright Copyright (c) 2023 深圳市酷瓜软件有限公司 * @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0 * @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com * @link https://www.koogua.com
*/ */
@ -11,12 +11,10 @@ use App\Models\Course as CourseModel;
use Phalcon\Mvc\Model\Resultset; use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface; use Phalcon\Mvc\Model\ResultsetInterface;
class FeaturedCourseList extends Cache class CourseRecommendedList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
protected $limit = 5;
public function getLifetime() public function getLifetime()
{ {
@ -25,17 +23,26 @@ class FeaturedCourseList extends Cache
public function getKey($id = null) public function getKey($id = null)
{ {
return 'featured_course_list'; return "course_recommended_list:{$id}";
} }
public function getContent($id = null) public function getContent($id = null)
{ {
$courses = $this->findCourses($this->limit); $courses = $this->findCourses(5);
if ($courses->count() == 0) { if ($courses->count() == 0) {
return []; return [];
} }
return $this->handleContent($courses);
}
/**
* @param CourseModel[] $courses
* @return array
*/
public function handleContent($courses)
{
$result = []; $result = [];
foreach ($courses as $course) { foreach ($courses as $course) {
@ -69,10 +76,10 @@ class FeaturedCourseList extends Cache
* @param int $limit * @param int $limit
* @return ResultsetInterface|Resultset|CourseModel[] * @return ResultsetInterface|Resultset|CourseModel[]
*/ */
protected function findCourses($limit = 5) public function findCourses($limit = 5)
{ {
return CourseModel::query() return CourseModel::query()
->where('featured = 1') ->where('market_price > 0')
->andWhere('published = 1') ->andWhere('published = 1')
->andWhere('deleted = 0') ->andWhere('deleted = 0')
->orderBy('RAND()') ->orderBy('RAND()')

View File

@ -13,7 +13,7 @@ use App\Repos\Course as CourseRepo;
class CourseRelatedList extends Cache class CourseRelatedList extends Cache
{ {
protected $lifetime = 86400; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -0,0 +1,63 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\User as UserModel;
use App\Repos\Course as CourseRepo;
class CourseTeacherList extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "course_teacher_list:{$id}";
}
public function getContent($id = null)
{
$courseRepo = new CourseRepo();
$users = $courseRepo->findTeachers($id);
if ($users->count() == 0) {
return [];
}
return $this->handleContent($users);
}
/**
* @param UserModel[] $users
* @return array
*/
public function handleContent($users)
{
$result = [];
foreach ($users as $user) {
$result[] = [
'id' => $user->id,
'name' => $user->name,
'avatar' => $user->avatar,
'vip' => $user->vip,
'title' => $user->title,
'about' => $user->about,
];
}
return $result;
}
}

View File

@ -14,7 +14,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class CourseTopicList extends Cache class CourseTopicList extends Cache
{ {
protected $lifetime = 86400; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -1,71 +0,0 @@
<?php
/**
* @copyright Copyright (c) 2023 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Article as ArticleModel;
use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface;
class FeaturedArticleList extends Cache
{
protected $lifetime = 3600;
protected $limit = 5;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'featured_article_list';
}
public function getContent($id = null)
{
$articles = $this->findArticles($this->limit);
if ($articles->count() == 0) {
return [];
}
$result = [];
foreach ($articles as $article) {
$result[] = [
'id' => $article->id,
'title' => $article->title,
'cover' => $article->cover,
'favorite_count' => $article->favorite_count,
'comment_count' => $article->comment_count,
'view_count' => $article->view_count,
'like_count' => $article->like_count,
];
}
return $result;
}
/**
* @param int $limit
* @return ResultsetInterface|Resultset|ArticleModel[]
*/
protected function findArticles($limit = 5)
{
return ArticleModel::query()
->where('featured = 1')
->andWhere('published = :published:', ['published' => ArticleModel::PUBLISH_APPROVED])
->andWhere('deleted = 0')
->orderBy('RAND()')
->limit($limit)
->execute();
}
}

View File

@ -1,72 +0,0 @@
<?php
/**
* @copyright Copyright (c) 2023 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Question as QuestionModel;
use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface;
class FeaturedQuestionList extends Cache
{
protected $lifetime = 3600;
protected $limit = 5;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'featured_question_list';
}
public function getContent($id = null)
{
$questions = $this->findQuestions($this->limit);
if ($questions->count() == 0) {
return [];
}
$result = [];
foreach ($questions as $question) {
$result[] = [
'id' => $question->id,
'title' => $question->title,
'cover' => $question->cover,
'favorite_count' => $question->favorite_count,
'answer_count' => $question->answer_count,
'view_count' => $question->view_count,
'like_count' => $question->like_count,
];
}
return $result;
}
/**
* @param int $limit
* @return ResultsetInterface|Resultset|QuestionModel[]
*/
protected function findQuestions($limit = 5)
{
return QuestionModel::query()
->where('featured = 1')
->andWhere('published = :published:', ['published' => QuestionModel::PUBLISH_APPROVED])
->andWhere('deleted = 0')
->orderBy('RAND()')
->limit($limit)
->execute();
}
}

36
app/Caches/FlashSale.php Normal file
View File

@ -0,0 +1,36 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Repos\FlashSale as FlashSaleRepo;
class FlashSale extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "flash_sale:{$id}";
}
public function getContent($id = null)
{
$saleRepo = new FlashSaleRepo();
$sale = $saleRepo->findById($id);
return $sale ?: null;
}
}

36
app/Caches/Help.php Normal file
View File

@ -0,0 +1,36 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Repos\Help as HelpRepo;
class Help extends Cache
{
protected $lifetime = 7 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "help:{$id}";
}
public function getContent($id = null)
{
$helpRepo = new HelpRepo();
$help = $helpRepo->findById($id);
return $help ?: null;
}
}

97
app/Caches/HelpList.php Normal file
View File

@ -0,0 +1,97 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Category as CategoryModel;
use App\Models\Help as HelpModel;
use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface;
class HelpList extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'help_list';
}
public function getContent($id = null)
{
$categories = $this->findCategories();
if ($categories->count() == 0) {
return [];
}
$result = [];
foreach ($categories as $category) {
$item = [];
$item['category'] = [
'id' => $category->id,
'name' => $category->name,
];
$item['helps'] = [];
$helps = $this->findHelps($category->id);
if ($helps->count() > 0) {
foreach ($helps as $help) {
$item['helps'][] = [
'id' => $help->id,
'title' => $help->title,
];
}
}
$result[] = $item;
}
return $result;
}
/**
* @return ResultsetInterface|Resultset|CategoryModel[]
*/
protected function findCategories()
{
return CategoryModel::query()
->where('type = :type:', ['type' => CategoryModel::TYPE_HELP])
->andWhere('level = 1')
->andWhere('published = 1')
->andWhere('deleted = 0')
->orderBy('priority ASC')
->execute();
}
/**
* @param int $categoryId
* @return ResultsetInterface|Resultset|CategoryModel[]
*/
protected function findHelps($categoryId)
{
return HelpModel::query()
->where('category_id = :category_id:', ['category_id' => $categoryId])
->andWhere('published = 1')
->andWhere('deleted = 0')
->orderBy('priority ASC')
->execute();
}
}

View File

@ -14,11 +14,13 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class HotQuestionList extends Cache class HotQuestionList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {
return $this->lifetime; $tomorrow = strtotime('tomorrow');
return $tomorrow - time();
} }
public function getKey($id = null) public function getKey($id = null)
@ -46,12 +48,6 @@ class HotQuestionList extends Cache
return $this->handleQuestions($questions); return $this->handleQuestions($questions);
} }
$questions = $this->findFullyHotQuestions();
if ($questions->count() > 0) {
return $this->handleQuestions($questions);
}
return []; return [];
} }
@ -106,17 +102,6 @@ class HotQuestionList extends Cache
return $this->findHotQuestions($createTime, $limit); return $this->findHotQuestions($createTime, $limit);
} }
/**
* @param int $limit
* @return ResultsetInterface|Resultset|QuestionModel[]
*/
protected function findFullyHotQuestions($limit = 10)
{
$createTime = 0;
return $this->findHotQuestions($createTime, $limit);
}
/** /**
* @param int $createTime * @param int $createTime
* @param int $limit * @param int $limit

View File

@ -0,0 +1,89 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\ImMessage;
use App\Models\ImMessage as ImMessageModel;
use App\Models\User as UserModel;
use App\Repos\ImGroup as ImGroupRepo;
use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface;
class ImActiveGroupList extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'im_active_group_list';
}
public function getContent($id = null)
{
$groups = $this->findGroups();
if (empty($groups)) return [];
$result = [];
foreach ($groups as $group) {
$result[] = [
'id' => $group->id,
'type' => $group->type,
'name' => $group->name,
'avatar' => $group->avatar,
'about' => $group->about,
'user_count' => $group->user_count,
'msg_count' => $group->msg_count,
];
}
return $result;
}
/**
* @param int $days
* @param int $limit
* @return ResultsetInterface|Resultset|UserModel[]
*/
protected function findGroups($days = 7, $limit = 12)
{
$result = [];
$startTime = strtotime("-{$days} days");
$endTime = time();
$rows = ImMessageModel::query()
->columns(['receiver_id', 'total_count' => 'count(receiver_id)'])
->groupBy('receiver_id')
->orderBy('total_count DESC')
->where('receiver_type = :type:', ['type' => ImMessageModel::TYPE_GROUP])
->betweenWhere('create_time', $startTime, $endTime)
->andWhere('deleted = 0')
->limit($limit)
->execute();
if ($rows->count() > 0) {
$ids = kg_array_column($rows->toArray(), 'receiver_id');
$groupRepo = new ImGroupRepo();
$result = $groupRepo->findByIds($ids);
}
return $result;
}
}

View File

@ -0,0 +1,85 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\ImMessage as ImMessageModel;
use App\Models\User as UserModel;
use App\Repos\User as UserRepo;
use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface;
class ImActiveUserList extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'im_active_user_list';
}
public function getContent($id = null)
{
$users = $this->findUsers($id);
if (empty($users)) return [];
$result = [];
foreach ($users as $user) {
$result[] = [
'id' => $user->id,
'name' => $user->name,
'avatar' => $user->avatar,
'title' => $user->title,
'about' => $user->about,
'vip' => $user->vip,
];
}
return $result;
}
/**
* @param int $days
* @param int $limit
* @return ResultsetInterface|Resultset|UserModel[]
*/
protected function findUsers($days = 7, $limit = 12)
{
$result = [];
$startTime = strtotime("-{$days} days");
$endTime = time();
$rows = ImMessageModel::query()
->columns(['sender_id', 'total_count' => 'count(sender_id)'])
->groupBy('sender_id')
->orderBy('total_count DESC')
->betweenWhere('create_time', $startTime, $endTime)
->limit($limit)
->execute();
if ($rows->count() > 0) {
$ids = kg_array_column($rows->toArray(), 'sender_id');
$userRepo = new UserRepo();
$result = $userRepo->findByIds($ids);
}
return $result;
}
}

36
app/Caches/ImGroup.php Normal file
View File

@ -0,0 +1,36 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Repos\ImGroup as ImGroupRepo;
class ImGroup extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "im_group:{$id}";
}
public function getContent($id = null)
{
$groupRepo = new ImGroupRepo();
$group = $groupRepo->findById($id);
return $group ?: null;
}
}

View File

@ -0,0 +1,88 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\ImMessage as ImMessageModel;
use App\Models\User as UserModel;
use App\Repos\User as UserRepo;
use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface;
class ImGroupActiveUserList extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "im_group_active_user_list:{$id}";
}
public function getContent($id = null)
{
$users = $this->findUsers($id);
if (empty($users)) return [];
$result = [];
foreach ($users as $user) {
$result[] = [
'id' => $user->id,
'name' => $user->name,
'avatar' => $user->avatar,
'title' => $user->title,
'about' => $user->about,
'vip' => $user->vip,
];
}
return $result;
}
/**
* @param int $groupId
* @param int $days
* @param int $limit
* @return ResultsetInterface|Resultset|UserModel[]
*/
protected function findUsers($groupId, $days = 7, $limit = 5)
{
$result = [];
$startTime = strtotime("-{$days} days");
$endTime = time();
$rows = ImMessageModel::query()
->columns(['sender_id', 'total_count' => 'count(sender_id)'])
->groupBy('sender_id')
->orderBy('total_count DESC')
->where('receiver_id = :group_id:', ['group_id' => $groupId])
->andWhere('receiver_type = :type:', ['type' => ImMessageModel::TYPE_GROUP])
->betweenWhere('create_time', $startTime, $endTime)
->limit($limit)
->execute();
if ($rows->count() > 0) {
$ids = kg_array_column($rows->toArray(), 'sender_id');
$userRepo = new UserRepo();
$result = $userRepo->findByIds($ids);
}
return $result;
}
}

View File

@ -0,0 +1,79 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\ImGroup as ImGroupModel;
use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface;
class ImNewGroupList extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'im_new_group_list';
}
public function getContent($id = null)
{
$limit = 12;
$groups = $this->findGroups($limit);
if ($groups->count() == 0) {
return [];
}
return $this->handleContent($groups);
}
/**
* @param ImGroupModel[] $groups
* @return array
*/
protected function handleContent($groups)
{
$result = [];
foreach ($groups as $group) {
$result[] = [
'id' => $group->id,
'type' => $group->type,
'name' => $group->name,
'avatar' => $group->avatar,
'about' => $group->about,
'user_count' => $group->user_count,
'msg_count' => $group->msg_count,
];
}
return $result;
}
/**
* @param int $limit
* @return ResultsetInterface|Resultset|ImGroupModel[]
*/
public function findGroups($limit = 12)
{
return ImGroupModel::query()
->where('published = 1')
->andWhere('deleted = 0')
->orderBy('id DESC')
->limit($limit)
->execute();
}
}

View File

@ -0,0 +1,77 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\User as UserModel;
use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface;
class ImNewUserList extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'im_new_user_list';
}
public function getContent($id = null)
{
$limit = 12;
$users = $this->findUsers($limit);
if ($users->count() == 0) {
return [];
}
return $this->handleContent($users);
}
/**
* @param UserModel[] $users
* @return array
*/
protected function handleContent($users)
{
$result = [];
foreach ($users as $user) {
$result[] = [
'id' => $user->id,
'name' => $user->name,
'avatar' => $user->avatar,
'title' => $user->title,
'about' => $user->about,
'vip' => $user->vip,
];
}
return $result;
}
/**
* @param int $limit
* @return ResultsetInterface|Resultset|UserModel[]
*/
public function findUsers($limit = 12)
{
return UserModel::query()
->where('deleted = 0')
->orderBy('id DESC')
->limit($limit)
->execute();
}
}

View File

@ -14,7 +14,7 @@ use App\Services\Logic\Article\ArticleList as ArticleListService;
class IndexArticleList extends Cache class IndexArticleList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 15 * 60;
public function getLifetime() public function getLifetime()
{ {

View File

@ -19,7 +19,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexFeaturedCourseList extends Cache class IndexFeaturedCourseList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -0,0 +1,36 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Services\Logic\FlashSale\SaleList;
class IndexFlashSaleList extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return strtotime('tomorrow') - time();
}
public function getKey($id = null)
{
return 'index_flash_sale_list';
}
public function getContent($id = null)
{
$service = new SaleList();
$sales = $service->handle();
return $sales[0]['items'] ?? [];
}
}

View File

@ -19,7 +19,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexFreeCourseList extends Cache class IndexFreeCourseList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -18,7 +18,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexLiveList extends Cache class IndexLiveList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -19,7 +19,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexNewCourseList extends Cache class IndexNewCourseList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -14,7 +14,7 @@ use App\Services\Logic\Question\QuestionList as QuestionListService;
class IndexQuestionList extends Cache class IndexQuestionList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 15 * 60;
public function getLifetime() public function getLifetime()
{ {

View File

@ -17,7 +17,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexSimpleFeaturedCourseList extends Cache class IndexSimpleFeaturedCourseList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -17,7 +17,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexSimpleFreeCourseList extends Cache class IndexSimpleFreeCourseList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -17,7 +17,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexSimpleNewCourseList extends Cache class IndexSimpleNewCourseList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -17,7 +17,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexSimpleVipCourseList extends Cache class IndexSimpleVipCourseList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -14,7 +14,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexSlideList extends Cache class IndexSlideList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 365 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -14,7 +14,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexTeacherList extends Cache class IndexTeacherList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 3600;
public function getLifetime() public function getLifetime()
{ {

View File

@ -19,7 +19,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class IndexVipCourseList extends Cache class IndexVipCourseList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -0,0 +1,34 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Answer as AnswerModel;
class MaxAnswerId extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'max_answer_id';
}
public function getContent($id = null)
{
$answer = AnswerModel::findFirst(['order' => 'id DESC']);
return $answer->id ?? 0;
}
}

View File

@ -0,0 +1,34 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Article as ArticleModel;
class MaxArticleId extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'max_article_id';
}
public function getContent($id = null)
{
$article = ArticleModel::findFirst(['order' => 'id DESC']);
return $article->id ?? 0;
}
}

View File

@ -0,0 +1,34 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Comment as CommentModel;
class MaxCommentId extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'max_comment_id';
}
public function getContent($id = null)
{
$comment = CommentModel::findFirst(['order' => 'id DESC']);
return $comment->id ?? 0;
}
}

View File

@ -0,0 +1,34 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\FlashSale as FlashSaleModel;
class MaxFlashSaleId extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'max_flash_sale_id';
}
public function getContent($id = null)
{
$sale = FlashSaleModel::findFirst(['order' => 'id DESC']);
return $sale->id ?? 0;
}
}

34
app/Caches/MaxHelpId.php Normal file
View File

@ -0,0 +1,34 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Help as HelpModel;
class MaxHelpId extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'max_help_id';
}
public function getContent($id = null)
{
$help = HelpModel::findFirst(['order' => 'id DESC']);
return $help->id ?? 0;
}
}

View File

@ -0,0 +1,34 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\ImGroup as ImGroupModel;
class MaxImGroupId extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'max_im_group_id';
}
public function getContent($id = null)
{
$group = ImGroupModel::findFirst(['order' => 'id DESC']);
return $group->id ?? 0;
}
}

34
app/Caches/MaxPageId.php Normal file
View File

@ -0,0 +1,34 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Page as PageModel;
class MaxPageId extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'max_page_id';
}
public function getContent($id = null)
{
$page = PageModel::findFirst(['order' => 'id DESC']);
return $page->id ?? 0;
}
}

View File

@ -0,0 +1,34 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\PointGift as PointGiftModel;
class MaxPointGiftId extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'max_point_gift_id';
}
public function getContent($id = null)
{
$gift = PointGiftModel::findFirst(['order' => 'id DESC']);
return $gift->id ?? 0;
}
}

View File

@ -0,0 +1,34 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Question as QuestionModel;
class MaxQuestionId extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'max_question_id';
}
public function getContent($id = null)
{
$question = QuestionModel::findFirst(['order' => 'id DESC']);
return $question->id ?? 0;
}
}

View File

@ -0,0 +1,34 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Models\Upload as UploadModel;
class MaxUploadId extends Cache
{
protected $lifetime = 365 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'max_upload_id';
}
public function getContent($id = null)
{
$upload = UploadModel::findFirst(['order' => 'id DESC']);
return $upload->id ?? 0;
}
}

View File

@ -0,0 +1,44 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Repos\Stat as StatRepo;
class ModerationStat extends Cache
{
protected $lifetime = 15 * 60;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return 'moderation_stat';
}
public function getContent($id = null)
{
$statRepo = new StatRepo();
$articleCount = $statRepo->countPendingArticles();
$questionCount = $statRepo->countPendingQuestions();
$answerCount = $statRepo->countPendingAnswers();
$commentCount = $statRepo->countPendingComments();
return [
'article_count' => $articleCount,
'question_count' => $questionCount,
'answer_count' => $answerCount,
'comment_count' => $commentCount,
];
}
}

View File

@ -13,7 +13,7 @@ use App\Repos\Package as PackageRepo;
class PackageCourseList extends Cache class PackageCourseList extends Cache
{ {
protected $lifetime = 86400; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

36
app/Caches/Page.php Normal file
View File

@ -0,0 +1,36 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Repos\Page as PageRepo;
class Page extends Cache
{
protected $lifetime = 7 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "page:{$id}";
}
public function getContent($id = null)
{
$pageRepo = new PageRepo();
$page = $pageRepo->findById($id);
return $page ?: null;
}
}

36
app/Caches/PointGift.php Normal file
View File

@ -0,0 +1,36 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Repos\PointGift as PointGiftRepo;
class PointGift extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "point_gift:{$id}";
}
public function getContent($id = null)
{
$giftRepo = new PointGiftRepo();
$gift = $giftRepo->findById($id);
return $gift ?: null;
}
}

View File

@ -19,7 +19,7 @@ class PointHotGiftList extends Cache
* *
* @var int * @var int
*/ */
protected $lifetime = 86400; protected $lifetime = 1 * 86400;
/** /**
* 显示个数 * 显示个数

36
app/Caches/Question.php Normal file
View File

@ -0,0 +1,36 @@
<?php
/**
* @copyright Copyright (c) 2021 深圳市酷瓜软件有限公司
* @license https://opensource.org/licenses/GPL-2.0
* @link https://www.koogua.com
*/
namespace App\Caches;
use App\Repos\Question as QuestionRepo;
class Question extends Cache
{
protected $lifetime = 1 * 86400;
public function getLifetime()
{
return $this->lifetime;
}
public function getKey($id = null)
{
return "question:{$id}";
}
public function getContent($id = null)
{
$questionRepo = new QuestionRepo();
$question = $questionRepo->findById($id);
return $question ?: null;
}
}

View File

@ -12,6 +12,7 @@ use App\Repos\Article as ArticleRepo;
use App\Repos\Comment as CommentRepo; use App\Repos\Comment as CommentRepo;
use App\Repos\Consult as ConsultRepo; use App\Repos\Consult as ConsultRepo;
use App\Repos\Course as CourseRepo; use App\Repos\Course as CourseRepo;
use App\Repos\ImGroup as GroupRepo;
use App\Repos\Package as PackageRepo; use App\Repos\Package as PackageRepo;
use App\Repos\Question as QuestionRepo; use App\Repos\Question as QuestionRepo;
use App\Repos\Review as ReviewRepo; use App\Repos\Review as ReviewRepo;
@ -41,6 +42,7 @@ class SiteGlobalStat extends Cache
$answerRepo = new AnswerRepo(); $answerRepo = new AnswerRepo();
$commentRepo = new CommentRepo(); $commentRepo = new CommentRepo();
$consultRepo = new ConsultRepo(); $consultRepo = new ConsultRepo();
$groupRepo = new GroupRepo();
$packageRepo = new PackageRepo(); $packageRepo = new PackageRepo();
$reviewRepo = new ReviewRepo(); $reviewRepo = new ReviewRepo();
$topicRepo = new TopicRepo(); $topicRepo = new TopicRepo();
@ -53,6 +55,7 @@ class SiteGlobalStat extends Cache
'answer_count' => $answerRepo->countAnswers(), 'answer_count' => $answerRepo->countAnswers(),
'comment_count' => $commentRepo->countComments(), 'comment_count' => $commentRepo->countComments(),
'consult_count' => $consultRepo->countConsults(), 'consult_count' => $consultRepo->countConsults(),
'group_count' => $groupRepo->countGroups(),
'vip_count' => $userRepo->countVipUsers(), 'vip_count' => $userRepo->countVipUsers(),
'package_count' => $packageRepo->countPackages(), 'package_count' => $packageRepo->countPackages(),
'review_count' => $reviewRepo->countReviews(), 'review_count' => $reviewRepo->countReviews(),

View File

@ -13,9 +13,9 @@ use App\Repos\Article as ArticleRepo;
class TaggedArticleList extends Cache class TaggedArticleList extends Cache
{ {
protected $limit = 15; protected $limit = 5;
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -13,9 +13,9 @@ use App\Repos\Question as QuestionRepo;
class TaggedQuestionList extends Cache class TaggedQuestionList extends Cache
{ {
protected $limit = 15; protected $limit = 5;
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -7,8 +7,8 @@
namespace App\Caches; namespace App\Caches;
use App\Models\Answer as AnswerModel; use App\Models\Article as ArticleModel;
use App\Models\AnswerLike as AnswerLikeModel; use App\Models\ArticleLike as ArticleLikeModel;
use App\Repos\User as UserRepo; use App\Repos\User as UserRepo;
use Phalcon\Mvc\Model\Resultset; use Phalcon\Mvc\Model\Resultset;
use Phalcon\Mvc\Model\ResultsetInterface; use Phalcon\Mvc\Model\ResultsetInterface;
@ -16,7 +16,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class TopAnswererList extends Cache class TopAnswererList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {
@ -37,24 +37,10 @@ class TopAnswererList extends Cache
return $this->handleUsers($userIds); return $this->handleUsers($userIds);
} }
$rankings = $this->findMonthlyAuthorRankings(); $randOwners = $this->findRandArticleOwners();
if ($rankings->count() > 0) { if ($randOwners->count() > 0) {
$userIds = kg_array_column($rankings->toArray(), 'author_id'); $userIds = kg_array_column($randOwners->toArray(), 'owner_id');
return $this->handleUsers($userIds);
}
$rankings = $this->findYearlyAuthorRankings();
if ($rankings->count() > 0) {
$userIds = kg_array_column($rankings->toArray(), 'author_id');
return $this->handleUsers($userIds);
}
$rankings = $this->findFullyAuthorRankings();
if ($rankings->count() > 0) {
$userIds = kg_array_column($rankings->toArray(), 'author_id');
return $this->handleUsers($userIds); return $this->handleUsers($userIds);
} }
@ -83,6 +69,19 @@ class TopAnswererList extends Cache
return $result; return $result;
} }
/**
* @param int $limit
* @return ResultsetInterface|Resultset
*/
protected function findRandArticleOwners($limit = 10)
{
return ArticleModel::query()
->columns(['owner_id'])
->orderBy('RAND()')
->limit($limit)
->execute();
}
/** /**
* @param int $limit * @param int $limit
* @return ResultsetInterface|Resultset * @return ResultsetInterface|Resultset
@ -91,49 +90,6 @@ class TopAnswererList extends Cache
{ {
$createTime = strtotime('monday this week'); $createTime = strtotime('monday this week');
return $this->findAuthorRankings($createTime, $limit);
}
/**
* @param int $limit
* @return ResultsetInterface|Resultset
*/
protected function findMonthlyAuthorRankings($limit = 10)
{
$createTime = strtotime(date('Y-m-01'));
return $this->findAuthorRankings($createTime, $limit);
}
/**
* @param int $limit
* @return ResultsetInterface|Resultset
*/
protected function findYearlyAuthorRankings($limit = 10)
{
$createTime = strtotime(date('Y-01-01'));
return $this->findAuthorRankings($createTime, $limit);
}
/**
* @param int $limit
* @return ResultsetInterface|Resultset
*/
protected function findFullyAuthorRankings($limit = 10)
{
$createTime = 0;
return $this->findAuthorRankings($createTime, $limit);
}
/**
* @param int $createTime
* @param int $limit
* @return ResultsetInterface|Resultset
*/
protected function findAuthorRankings($createTime, $limit = 10)
{
$columns = [ $columns = [
'author_id' => 'a.owner_id', 'author_id' => 'a.owner_id',
'like_count' => 'count(al.user_id)', 'like_count' => 'count(al.user_id)',
@ -141,8 +97,8 @@ class TopAnswererList extends Cache
return $this->modelsManager->createBuilder() return $this->modelsManager->createBuilder()
->columns($columns) ->columns($columns)
->addFrom(AnswerLikeModel::class, 'al') ->addFrom(ArticleLikeModel::class, 'al')
->join(AnswerModel::class, 'al.answer_id = a.id', 'a') ->join(ArticleModel::class, 'al.article_id = a.id', 'a')
->where('al.create_time > :create_time:', ['create_time' => $createTime]) ->where('al.create_time > :create_time:', ['create_time' => $createTime])
->groupBy('author_id') ->groupBy('author_id')
->orderBy('like_count DESC') ->orderBy('like_count DESC')

View File

@ -16,7 +16,7 @@ use Phalcon\Mvc\Model\ResultsetInterface;
class TopAuthorList extends Cache class TopAuthorList extends Cache
{ {
protected $lifetime = 3600; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -12,7 +12,7 @@ use App\Repos\User as UserRepo;
class User extends Cache class User extends Cache
{ {
protected $lifetime = 86400; protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {

View File

@ -10,6 +10,8 @@ namespace App\Caches;
class UserDailyCounter extends Counter class UserDailyCounter extends Counter
{ {
protected $lifetime = 1 * 86400;
public function getLifetime() public function getLifetime()
{ {
$tomorrow = strtotime('tomorrow'); $tomorrow = strtotime('tomorrow');

View File

@ -1,42 +0,0 @@
<?php
/**
* @copyright Copyright (c) 2022 深圳市酷瓜软件有限公司
* @license https://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* @link https://www.koogua.com
*/
namespace App\Console\Migrations;
use App\Models\Setting as SettingModel;
use App\Repos\Setting as SettingRepo;
use App\Traits\Service as ServiceTrait;
abstract class Migration
{
use ServiceTrait;
abstract public function run();
protected function saveSettings(array $settings)
{
foreach ($settings as $setting) {
$this->saveSetting($setting);
}
}
protected function saveSetting(array $setting)
{
$settingRepo = new SettingRepo();
$item = $settingRepo->findItem($setting['section'], $setting['item_key']);
if (!$item) {
$item = new SettingModel();
$item->create($setting);
} else {
$item->update($setting);
}
}
}

View File

@ -1,48 +0,0 @@
<?php
/**
* @copyright Copyright (c) 2024 深圳市酷瓜软件有限公司
* @license https://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* @link https://www.koogua.com
*/
namespace App\Console\Migrations;
use App\Models\Chapter as ChapterModel;
use App\Models\Course as CourseModel;
use Phalcon\Mvc\Model\Resultset;
class V20240608145810 extends Migration
{
public function run()
{
$this->handleReadChapters();
}
protected function handleReadChapters()
{
/**
* @var $chapters Resultset|ChapterModel[]
*/
$chapters = ChapterModel::query()
->where('model = :model:', ['model' => CourseModel::MODEL_READ])
->andWhere('parent_id > 0')
->execute();
if ($chapters->count() == 0) return;
foreach ($chapters as $chapter) {
$attrs = $chapter->attrs;
if (isset($attrs['format'])) continue;
$attrs['format'] = 'html';
$chapter->attrs = $attrs;
$chapter->update();
}
}
}

View File

@ -1,29 +0,0 @@
<?php
/**
* @copyright Copyright (c) 2024 深圳市酷瓜软件有限公司
* @license https://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* @link https://www.koogua.com
*/
namespace App\Console\Migrations;
class V20241110191316 extends Migration
{
public function run()
{
$this->handleContactSettings();
}
protected function handleContactSettings()
{
$setting = [
'section' => 'contact',
'item_key' => 'douyin',
'item_value' => '',
];
$this->saveSetting($setting);
}
}

View File

@ -1,41 +0,0 @@
<?php
/**
* @copyright Copyright (c) 2025 深圳市酷瓜软件有限公司
* @license https://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* @link https://www.koogua.com
*/
namespace App\Console\Migrations;
use App\Models\UserBalance;
use App\Repos\User as UserRepo;
class V20250110191618 extends Migration
{
public function run()
{
$this->handleRootUserBalance();
}
/**
* 之前migration初始化root账号缺少user_balance数据
*/
protected function handleRootUserBalance()
{
$userId = 10000;
$userRepo = new UserRepo();
$userBalance = $userRepo->findUserBalance($userId);
if ($userBalance) return;
$userBalance = new UserBalance();
$userBalance->user_id = $userId;
$userBalance->create();
}
}

Some files were not shown because too many files have changed in this diff Show More