Unify success codes and update upload deps
This commit is contained in:
@@ -10,3 +10,5 @@
|
||||
rate limit功能
|
||||
|
||||
rss功能
|
||||
|
||||
完成开发后记得Debug=False
|
||||
|
||||
45
back/main.py
45
back/main.py
@@ -8,6 +8,8 @@ import os
|
||||
import uuid
|
||||
import json
|
||||
import filetype
|
||||
from PIL import Image
|
||||
from PIL import UnidentifiedImageError
|
||||
from datetime import datetime
|
||||
|
||||
app = Flask(__name__)
|
||||
@@ -212,6 +214,23 @@ def save_hashtags(tag_type, target_id, hashtopic):
|
||||
)
|
||||
db.session.add(new_tag)
|
||||
|
||||
def mime_allowed(mime, rules):
|
||||
if not rules:
|
||||
return True
|
||||
if not mime:
|
||||
return False
|
||||
mime = mime.lower()
|
||||
for rule in rules:
|
||||
rule = str(rule).strip().lower()
|
||||
if not rule:
|
||||
continue
|
||||
if rule == 'image/*':
|
||||
if mime.startswith('image/'):
|
||||
return True
|
||||
if mime == rule:
|
||||
return True
|
||||
return False
|
||||
|
||||
# --- 用户普通api端点 ---
|
||||
@app.route('/api/settings', methods=['GET'])
|
||||
def get_settings():
|
||||
@@ -244,7 +263,7 @@ def get_about():
|
||||
"data": settings.about
|
||||
})
|
||||
else:
|
||||
# about在初始化时不会被设置,避免管理面板报错,返回默认文本
|
||||
# about在初始化时不会被设置,避免报错,返回默认文本
|
||||
return jsonify({
|
||||
"code": 1000,
|
||||
"data": "# 默认关于页面\n关于页面未设置,请前往管理面板操作。"
|
||||
@@ -354,7 +373,7 @@ def submit_post():
|
||||
save_hashtags(0, new_post.id, hashtopic)
|
||||
db.session.commit()
|
||||
|
||||
code = 1002 if new_post.status == 'Pending' else 1001
|
||||
code = 1002 if new_post.status == 'Pending' else 1000
|
||||
return jsonify({"code": code, "data": {"id": new_post.id}})
|
||||
except Exception as e:
|
||||
db.session.rollback()
|
||||
@@ -409,7 +428,7 @@ def submit_comment():
|
||||
save_hashtags(1, new_comment.id, hashtopic)
|
||||
db.session.commit()
|
||||
|
||||
return jsonify({"code": 1001, "data": {"id": new_comment.id}})
|
||||
return jsonify({"code": 1000, "data": {"id": new_comment.id}})
|
||||
except Exception as e:
|
||||
db.session.rollback()
|
||||
return jsonify({"code": 2003, "data": f"评论失败: {str(e)}"})
|
||||
@@ -448,7 +467,7 @@ def submit_report():
|
||||
db.session.add(report)
|
||||
db.session.commit()
|
||||
|
||||
return jsonify({"code": 1001, "data": {"id": report.id}})
|
||||
return jsonify({"code": 1000, "data": {"id": report.id}})
|
||||
except Exception as e:
|
||||
return jsonify({"code": 2003, "data": f"投诉失败: {str(e)}"})
|
||||
|
||||
@@ -499,15 +518,27 @@ def upload_pic():
|
||||
if FILE_SIZE_LIMIT_MB is not None:
|
||||
limit_bytes = float(FILE_SIZE_LIMIT_MB) * 1024 * 1024
|
||||
if file_length > limit_bytes:
|
||||
return jsonify({"code": 2006, "data": "上传的图片超出限制大小"})
|
||||
return jsonify({"code": 2006, "data": f"上传的图片超出{FILE_SIZE_LIMIT_MB}MB限制大小"})
|
||||
|
||||
ext = os.path.splitext(file.filename)[1].lstrip('.').lower()
|
||||
kind = filetype.guess(file.read(5120))
|
||||
file.seek(0)
|
||||
detected_mime = kind.mime if kind else None
|
||||
if not detected_mime or (FILE_FORMATS and detected_mime.lower() not in FILE_FORMATS):
|
||||
if not detected_mime or not mime_allowed(detected_mime, FILE_FORMATS):
|
||||
return jsonify({"code": 2007, "data": "上传的文件类型不支持"})
|
||||
|
||||
try:
|
||||
file.seek(0)
|
||||
img = Image.open(file)
|
||||
img.verify()
|
||||
file.seek(0)
|
||||
except (UnidentifiedImageError, OSError):
|
||||
file.seek(0)
|
||||
return jsonify({"code": 2008, "data": "上传的文件损坏"})
|
||||
except Exception:
|
||||
file.seek(0)
|
||||
return jsonify({"code": 2008, "data": "上传的文件损坏"})
|
||||
|
||||
if not ext and kind:
|
||||
ext = kind.extension
|
||||
filename = f"{uuid.uuid4().hex}.{ext}" if ext else uuid.uuid4().hex
|
||||
@@ -519,7 +550,7 @@ def upload_pic():
|
||||
db.session.add(ImgFile(path=filename, name=name, identity_token=identity_token))
|
||||
db.session.commit()
|
||||
|
||||
return jsonify({"code": 1001, "data": f"/api/files/{filename}"})
|
||||
return jsonify({"code": 1000, "data": f"/api/files/{filename}"})
|
||||
except Exception as e:
|
||||
return jsonify({"code": 2003, "data": str(e)})
|
||||
|
||||
|
||||
@@ -2,3 +2,4 @@ Flask>=3.0.3
|
||||
Flask-CORS>=4.0.1
|
||||
Flask-SQLAlchemy>=3.1.1
|
||||
filetype>=1.2.0
|
||||
Pillow>=10.0.0
|
||||
|
||||
@@ -28,18 +28,17 @@
|
||||
|
||||
| Code | 含义 |
|
||||
| ---- | ---------------------------------------------------- |
|
||||
| 1000 | 正常。适用于大多数成功的GET请求的返回。 |
|
||||
| 1001 | 正常。适用于大多数成功的POST请求的返回。 |
|
||||
| 1000 | 正常。适用于大多数成功的请求的返回。 |
|
||||
| 1002 | 正常。提交内容需要等待审核。 |
|
||||
| 2000 | 失败。请求方式错误,例如缺少指定参数。 |
|
||||
| 2000 | 失败。请求格式错误,例如缺少指定参数。 |
|
||||
| 2001 | 失败。未初始化。不应该在成功初始化后继续使用该code。 |
|
||||
| 2002 | 失败。数据不存在。 |
|
||||
| 2003 | 失败。服务器内部错误。 |
|
||||
| 2003 | 失败。服务器内部错误。表示未预期的服务端异常,不应频繁出现。 |
|
||||
| 2004 | 失败。试图使用不存在的Identity。 |
|
||||
| 2005 | 失败。提交内容包含违禁词。 |
|
||||
| 2006 | 失败。上传的图片超出限制大小。 |
|
||||
| 2007 | 失败。上传的文件类型不支持。 |
|
||||
| 404 | api端点不存在。 |
|
||||
| 2007 | 失败。上传的图片类型不支持。 |
|
||||
| 2008 | 失败。上传的图片损坏。 |
|
||||
| | |
|
||||
| | |
|
||||
| | |
|
||||
|
||||
@@ -431,7 +431,7 @@ export const postComment = async (commentData: PostCommentRequest): Promise<Post
|
||||
|
||||
const json = await response.json();
|
||||
handlePostApiCode(json);
|
||||
if (json.code === 1001 && json.data?.id !== undefined) {
|
||||
if (json.code === 1000 && json.data?.id !== undefined) {
|
||||
return { id: Number(json.data.id) };
|
||||
}
|
||||
if (json.code === 2005) {
|
||||
@@ -466,7 +466,7 @@ export const reportPost = async (reportData: { id: number; title: string; conten
|
||||
}
|
||||
const json = await response.json();
|
||||
handlePostApiCode(json);
|
||||
if (json.code === 1001 && json.data?.id !== undefined) {
|
||||
if (json.code === 1000 && json.data?.id !== undefined) {
|
||||
return { id: Number(json.data.id) };
|
||||
}
|
||||
throw new Error(json.data || 'Report failed');
|
||||
@@ -493,12 +493,15 @@ export const uploadImage = async (file: File): Promise<string> => {
|
||||
}
|
||||
const json = await response.json();
|
||||
handlePostApiCode(json);
|
||||
if (json.code === 1001 && typeof json.data === 'string') {
|
||||
if (json.code === 1000 && typeof json.data === 'string') {
|
||||
return json.data;
|
||||
}
|
||||
if (json.code === 2006) {
|
||||
throw new Error('UPLOAD_TOO_LARGE');
|
||||
}
|
||||
if (json.code === 2008) {
|
||||
throw new Error('CORRUPTED_IMAGE');
|
||||
}
|
||||
if (json.code === 2007) {
|
||||
throw new Error('UNSUPPORTED_FORMAT');
|
||||
}
|
||||
|
||||
@@ -214,7 +214,7 @@ const CreatePost: React.FC = () => {
|
||||
|
||||
try {
|
||||
const response = await createPost(value);
|
||||
if (response.code === 1001 || response.code === 1002) {
|
||||
if (response.code === 1000 || response.code === 1002) {
|
||||
// 清除草稿
|
||||
saveDraft('');
|
||||
setValue('');
|
||||
@@ -318,6 +318,13 @@ const CreatePost: React.FC = () => {
|
||||
</Toast>,
|
||||
{ intent: 'error' }
|
||||
);
|
||||
} else if (msg.includes('CORRUPTED_IMAGE')) {
|
||||
dispatchToast(
|
||||
<Toast>
|
||||
<ToastTitle>上传的文件损坏</ToastTitle>
|
||||
</Toast>,
|
||||
{ intent: 'error' }
|
||||
);
|
||||
} else if (msg.includes('UNSUPPORTED_FORMAT')) {
|
||||
dispatchToast(
|
||||
<Toast>
|
||||
|
||||
Reference in New Issue
Block a user