mirror of
https://gitee.com/ulthon/ulthon_information.git
synced 2026-07-01 14:42:48 +08:00
- Add content_type column to ul_post via migration - Install league/commonmark for markdown->HTML conversion - Add Post model accessors/setters for content_type and content - Update API Articles controller save/update with content_type support - Update API docs with content_type parameter and markdown example Closes content-type-support plan
264 lines
7.8 KiB
PHP
264 lines
7.8 KiB
PHP
<?php
|
|
|
|
declare(strict_types=1);
|
|
|
|
namespace app\api\controller;
|
|
|
|
use app\BaseController;
|
|
use app\model\Post;
|
|
use app\model\PostCategory;
|
|
use app\model\PostTag;
|
|
use League\CommonMark\CommonMarkConverter;
|
|
use think\Request;
|
|
|
|
class Articles extends BaseController
|
|
{
|
|
protected $middleware = [\app\middleware\ApiKeyAuth::class];
|
|
|
|
/**
|
|
* 文章列表
|
|
*/
|
|
public function index(Request $request)
|
|
{
|
|
$page = $request->param('page', 1, 'intval');
|
|
$limit = $request->param('limit', 15, 'intval');
|
|
$type = $request->param('type', '');
|
|
$category_id = $request->param('category_id', 0, 'intval');
|
|
$keyword = $request->param('keyword', '');
|
|
|
|
$model_list = Post::with(['categorys.category', 'tags.tag'])
|
|
->order('id desc');
|
|
|
|
if (!empty($type)) {
|
|
$model_list = $model_list->where('type', $type);
|
|
}
|
|
if (!empty($category_id)) {
|
|
$model_list = $model_list->where('category_id', $category_id);
|
|
}
|
|
if (!empty($keyword)) {
|
|
$model_list = $model_list->where('title', 'like', "%{$keyword}%");
|
|
}
|
|
|
|
$list = $model_list->paginate([
|
|
'page' => $page,
|
|
'list_rows' => $limit,
|
|
]);
|
|
|
|
return json_message([
|
|
'list' => $list->items(),
|
|
'total' => $list->total(),
|
|
'page' => $page,
|
|
]);
|
|
}
|
|
|
|
/**
|
|
* 文章详情
|
|
*/
|
|
public function read(Request $request)
|
|
{
|
|
$id = $request->param('id', 0, 'intval');
|
|
if ($id <= 0) {
|
|
return json_message('参数错误');
|
|
}
|
|
|
|
$post = Post::with(['categorys.category', 'tags.tag'])->find($id);
|
|
if (empty($post)) {
|
|
return json_message('文章不存在');
|
|
}
|
|
|
|
return json_message(['post' => $post]);
|
|
}
|
|
|
|
/**
|
|
* 创建文章
|
|
*/
|
|
public function save(Request $request)
|
|
{
|
|
if ($request->can_write_own != 1) {
|
|
return json_message('无权操作', 403);
|
|
}
|
|
|
|
$post_data = $request->post();
|
|
|
|
if (empty($post_data['title'])) {
|
|
return json_message('标题必填');
|
|
}
|
|
|
|
$categorys = [];
|
|
$tags = [];
|
|
if (isset($post_data['categorys'])) {
|
|
$categorys = $post_data['categorys'];
|
|
unset($post_data['categorys']);
|
|
}
|
|
if (isset($post_data['tags'])) {
|
|
$tags = $post_data['tags'];
|
|
unset($post_data['tags']);
|
|
}
|
|
|
|
$post_data['uid'] = uniqid();
|
|
$post_data['source'] = 'api';
|
|
$post_data['create_time'] = time();
|
|
$post_data['update_time'] = time();
|
|
|
|
if (!isset($post_data['type'])) {
|
|
$post_data['type'] = '1';
|
|
}
|
|
if (!isset($post_data['status'])) {
|
|
$post_data['status'] = 0;
|
|
}
|
|
if (!isset($post_data['content_type'])) {
|
|
$post_data['content_type'] = 'html';
|
|
}
|
|
|
|
// content_type 白名单校验
|
|
$allowed_content_types = ['html', 'markdown'];
|
|
if (!in_array($post_data['content_type'], $allowed_content_types)) {
|
|
return json_message('无效的content_type', 500);
|
|
}
|
|
|
|
// Markdown→HTML 自动转换
|
|
if ($post_data['content_type'] === 'markdown' && !empty($post_data['content'])) {
|
|
$converter = new CommonMarkConverter(['html_input' => 'strip', 'allow_unsafe_links' => false]);
|
|
$post_data['content_html'] = $converter->convert($post_data['content']);
|
|
}
|
|
|
|
$model_post = Post::create($post_data);
|
|
|
|
foreach ($categorys as $category) {
|
|
PostCategory::create([
|
|
'post_id' => $model_post->id,
|
|
'category_id' => $category,
|
|
]);
|
|
}
|
|
foreach ($tags as $tag) {
|
|
PostTag::create([
|
|
'post_id' => $model_post->id,
|
|
'tag_id' => $tag,
|
|
]);
|
|
}
|
|
|
|
return json_message(['id' => $model_post->id, 'uid' => $model_post->uid], 0, '创建成功');
|
|
}
|
|
|
|
/**
|
|
* 编辑文章
|
|
*/
|
|
public function update(Request $request)
|
|
{
|
|
$id = $request->param('id', 0, 'intval');
|
|
if ($id <= 0) {
|
|
return json_message('参数错误');
|
|
}
|
|
|
|
$model_post = Post::find($id);
|
|
if (empty($model_post)) {
|
|
return json_message('文章不存在');
|
|
}
|
|
|
|
$source = $model_post->getData('source');
|
|
if ($source === 'api') {
|
|
if ($request->can_write_own != 1) {
|
|
return json_message('无权操作', 403);
|
|
}
|
|
} else {
|
|
if ($request->can_write_other != 1) {
|
|
return json_message('无权操作', 403);
|
|
}
|
|
}
|
|
|
|
$post_data = $request->post();
|
|
unset($post_data['id']);
|
|
|
|
// categorys diff update
|
|
if (isset($post_data['categorys'])) {
|
|
$categorys = $post_data['categorys'];
|
|
unset($post_data['categorys']);
|
|
|
|
$old_category_list = PostCategory::where('post_id', $id)->select();
|
|
$old_category_ids = array_column($old_category_list->toArray(), 'category_id');
|
|
|
|
// old has, new doesn't -> delete
|
|
foreach ($old_category_list as $model_category) {
|
|
if (!in_array($model_category->category_id, $categorys)) {
|
|
$model_category->delete();
|
|
}
|
|
}
|
|
// new has, old doesn't -> create
|
|
foreach ($categorys as $category) {
|
|
if (!in_array($category, $old_category_ids)) {
|
|
PostCategory::create([
|
|
'post_id' => $id,
|
|
'category_id' => $category,
|
|
]);
|
|
}
|
|
}
|
|
}
|
|
|
|
// tags diff update
|
|
if (isset($post_data['tags'])) {
|
|
$tags = $post_data['tags'];
|
|
unset($post_data['tags']);
|
|
|
|
$old_tag_list = PostTag::where('post_id', $id)->select();
|
|
$old_tag_ids = array_column($old_tag_list->toArray(), 'tag_id');
|
|
|
|
foreach ($old_tag_list as $model_tag) {
|
|
if (!in_array($model_tag->tag_id, $tags)) {
|
|
$model_tag->delete();
|
|
}
|
|
}
|
|
foreach ($tags as $tag) {
|
|
if (!in_array($tag, $old_tag_ids)) {
|
|
PostTag::create([
|
|
'post_id' => $id,
|
|
'tag_id' => $tag,
|
|
]);
|
|
}
|
|
}
|
|
}
|
|
|
|
// Markdown→HTML 自动转换
|
|
if (isset($post_data['content_type']) && $post_data['content_type'] === 'markdown' && !empty($post_data['content'])) {
|
|
$converter = new CommonMarkConverter(['html_input' => 'strip', 'allow_unsafe_links' => false]);
|
|
$post_data['content_html'] = $converter->convert($post_data['content']);
|
|
}
|
|
|
|
$model_post->save($post_data);
|
|
|
|
return json_message([], 0, '更新成功');
|
|
}
|
|
|
|
/**
|
|
* 删除文章
|
|
*/
|
|
public function delete(Request $request)
|
|
{
|
|
$id = $request->param('id', 0, 'intval');
|
|
if ($id <= 0) {
|
|
return json_message('参数错误');
|
|
}
|
|
|
|
$model_post = Post::find($id);
|
|
if (empty($model_post)) {
|
|
return json_message('文章不存在');
|
|
}
|
|
|
|
$source = $model_post->getData('source');
|
|
if ($source === 'api') {
|
|
if ($request->can_delete < 1) {
|
|
return json_message('无权删除', 403);
|
|
}
|
|
} else {
|
|
if ($request->can_delete != 2) {
|
|
return json_message('无权删除', 403);
|
|
}
|
|
}
|
|
|
|
$model_post->delete();
|
|
PostCategory::where('post_id', $id)->delete();
|
|
PostTag::where('post_id', $id)->delete();
|
|
|
|
return json_message([], 0, '删除成功');
|
|
}
|
|
}
|