revise_chip_refresh
Change-Id: I8c3e5edecbd31f91519b5671686b2d72a88693e0
diff --git a/API/API-TRM/.gitignore b/API/API-TRM/.gitignore
deleted file mode 100644
index efc0820..0000000
--- a/API/API-TRM/.gitignore
+++ /dev/null
@@ -1,10 +0,0 @@
-node_modules/
-.vscode/
-dist/
-*.log
-.DS_Store
-.env
-.env.local
-.env.production
-.env.development
-package-lock.json
diff --git a/API/API-TRM/TRM/Back/app/__pycache__/routes.cpython-310.pyc b/API/API-TRM/TRM/Back/app/__pycache__/routes.cpython-310.pyc
deleted file mode 100644
index af72069..0000000
--- a/API/API-TRM/TRM/Back/app/__pycache__/routes.cpython-310.pyc
+++ /dev/null
Binary files differ
diff --git a/API/API-TRM/TRM/Back/app/functions/__pycache__/Fpost.cpython-310.pyc b/API/API-TRM/TRM/Back/app/functions/__pycache__/Fpost.cpython-310.pyc
deleted file mode 100644
index 2b6cd6d..0000000
--- a/API/API-TRM/TRM/Back/app/functions/__pycache__/Fpost.cpython-310.pyc
+++ /dev/null
Binary files differ
diff --git a/API/API-TRM/TRM/Back/app/routes.py b/API/API-TRM/TRM/Back/app/routes.py
deleted file mode 100644
index 1238364..0000000
--- a/API/API-TRM/TRM/Back/app/routes.py
+++ /dev/null
@@ -1,44 +0,0 @@
-from flask import Blueprint, render_template
-from .functions.Fpost import Fpost;
-from sqlalchemy import create_engine
-from sqlalchemy.orm import sessionmaker
-from config import Config
-from flask import jsonify,request
-
-main = Blueprint('main', __name__)
-
-
-@main.route('/spostlist',methods=['POST','GET'])
-def postlist():
- data=request.get_json()
- engine=create_engine(Config.SQLURL)
- SessionLocal = sessionmaker(bind=engine)
- session = SessionLocal()
- f=Fpost(session)
- checres=f.checkid(data['userid'])
- if(not checres):
- return jsonify()
- res=f.getlist()
- respons=[]
- for datai in res:
- respons.append({
- 'id': datai[0],
- 'title': datai[1],
- 'status': datai[2]
- })
- return jsonify(respons)
-
-@main.route('/sgetpost',methods=['POST','GET'])
-def post():
- data=request.get_json()
- engine=create_engine(Config.SQLURL)
- SessionLocal = sessionmaker(bind=engine)
- session = SessionLocal()
- f=Fpost(session)
- checres=f.checkid(data['userid'])
- if(not checres):
- return jsonify()
- res=f.getpost(data['postid'])
-
- return jsonify(res.to_dict() if res else {})
-
diff --git a/API/API-TRM/TRM/Back/tests/__pycache__/test_app.cpython-312-pytest-7.4.4.pyc b/API/API-TRM/TRM/Back/tests/__pycache__/test_app.cpython-312-pytest-7.4.4.pyc
deleted file mode 100644
index b21ba04..0000000
--- a/API/API-TRM/TRM/Back/tests/__pycache__/test_app.cpython-312-pytest-7.4.4.pyc
+++ /dev/null
Binary files differ
diff --git a/API/API-TRM/TRM/Front/trm-front/src/App.js b/API/API-TRM/TRM/Front/trm-front/src/App.js
deleted file mode 100644
index 3784575..0000000
--- a/API/API-TRM/TRM/Front/trm-front/src/App.js
+++ /dev/null
@@ -1,25 +0,0 @@
-import logo from './logo.svg';
-import './App.css';
-
-function App() {
- return (
- <div className="App">
- <header className="App-header">
- <img src={logo} className="App-logo" alt="logo" />
- <p>
- Edit <code>src/App.js</code> and save to reload.
- </p>
- <a
- className="App-link"
- href="https://reactjs.org"
- target="_blank"
- rel="noopener noreferrer"
- >
- Learn React
- </a>
- </header>
- </div>
- );
-}
-
-export default App;
diff --git a/API/API-TRM/TRM/Front/trm-front/src/index.js b/API/API-TRM/TRM/Front/trm-front/src/index.js
deleted file mode 100644
index d563c0f..0000000
--- a/API/API-TRM/TRM/Front/trm-front/src/index.js
+++ /dev/null
@@ -1,17 +0,0 @@
-import React from 'react';
-import ReactDOM from 'react-dom/client';
-import './index.css';
-import App from './App';
-import reportWebVitals from './reportWebVitals';
-
-const root = ReactDOM.createRoot(document.getElementById('root'));
-root.render(
- <React.StrictMode>
- <App />
- </React.StrictMode>
-);
-
-// If you want to start measuring performance in your app, pass a function
-// to log results (for example: reportWebVitals(console.log))
-// or send to an analytics endpoint. Learn more: https://bit.ly/CRA-vitals
-reportWebVitals();
diff --git a/API/API-TRM/all_tables.sql b/API/API-TRM/all_tables.sql
deleted file mode 100644
index f1e8547..0000000
--- a/API/API-TRM/all_tables.sql
+++ /dev/null
@@ -1,181 +0,0 @@
-/*
-数据库设计说明:
-1. 核心表结构:
- users:存储用户信息,包含角色管理和账号状态
- posts:核心内容表,支持多模态内容(图文/视频/文档)
- behaviors:记录用户互动行为(点赞/收藏/浏览等)
- comments:评论系统,支持多级回复
- follows:用户社交关系
-2. 推荐系统支持:
- posts.heat 字段存储动态计算的热度值
- behaviors 表记录用户行为用于协同过滤
- user_tags 表构建用户兴趣画像
- 通过 post_tags 实现内容标签分类
-3. 多模态内容处理:
- posts.media_urls 使用 JSON 类型存储多个资源 URL
- posts.type 区分不同类型的内容(图文/视频/文档)
-4. 审核与安全:
- audits 表记录内容审核历史
- posts.status 管理内容生命周期状态
- logs 表记录系统操作和访问日志
-5. 性能优化:
- 为查询频繁字段添加索引(热度/行为类型/时间)
- 使用 JSON 类型存储灵活数据(通知内容/媒体资源)
- 通过 heat 字段预计算支持热门排序
-6. 扩展性设计:
- 用户画像系统通过 user_tags 表实现
- 通知系统支持多种互动类型
- 行为表设计支持未来扩展新行为类型
-*/
-
-
--- 创建数据库
-CREATE DATABASE IF NOT EXISTS redbook DEFAULT CHARSET utf8mb4 COLLATE utf8mb4_general_ci;
-USE redbook;
-
--- 用户表
-CREATE TABLE users (
- id INT AUTO_INCREMENT PRIMARY KEY COMMENT '用户ID',
- username VARCHAR(50) NOT NULL UNIQUE COMMENT '用户名',
- password VARCHAR(255) NOT NULL COMMENT '加密密码',
- email VARCHAR(100) NOT NULL UNIQUE COMMENT '邮箱',
- avatar VARCHAR(255) COMMENT '头像URL',
- role ENUM('user', 'admin') DEFAULT 'user' COMMENT '角色',
- bio VARCHAR(255) COMMENT '个人简介',
- status ENUM('active', 'banned', 'muted') DEFAULT 'active' COMMENT '账号状态',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
- updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间'
-) ENGINE=InnoDB COMMENT='用户表';
-
--- 标签表
-CREATE TABLE tags (
- id INT AUTO_INCREMENT PRIMARY KEY COMMENT '标签ID',
- name VARCHAR(50) NOT NULL UNIQUE COMMENT '标签名称',
- description VARCHAR(255) COMMENT '标签描述',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间'
-) ENGINE=InnoDB COMMENT='内容标签表';
-
--- 话题/超话表
-CREATE TABLE topics (
- id INT AUTO_INCREMENT PRIMARY KEY COMMENT '话题ID',
- name VARCHAR(100) NOT NULL UNIQUE COMMENT '话题名称',
- description TEXT COMMENT '话题描述',
- status ENUM('active', 'archived') DEFAULT 'active' COMMENT '状态',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间'
-) ENGINE=InnoDB COMMENT='话题/超话表';
-
--- 内容帖子表
-CREATE TABLE posts (
- id INT AUTO_INCREMENT PRIMARY KEY COMMENT '帖子ID',
- user_id INT NOT NULL COMMENT '作者ID',
- topic_id INT COMMENT '所属话题ID',
- type ENUM('text', 'image', 'video', 'document') DEFAULT 'text' COMMENT '内容类型',
- title VARCHAR(255) NOT NULL COMMENT '标题',
- content TEXT NOT NULL COMMENT '正文内容',
- media_urls JSON COMMENT '媒体资源URL数组',
- status ENUM('draft', 'pending', 'published', 'deleted', 'rejected') DEFAULT 'draft' COMMENT '状态',
- heat INT DEFAULT 0 COMMENT '热度值',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
- updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
- FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE,
- FOREIGN KEY (topic_id) REFERENCES topics(id) ON DELETE SET NULL
-) ENGINE=InnoDB COMMENT='内容帖子表';
-
--- 帖子标签关联表
-CREATE TABLE post_tags (
- post_id INT NOT NULL COMMENT '帖子ID',
- tag_id INT NOT NULL COMMENT '标签ID',
- PRIMARY KEY (post_id, tag_id),
- FOREIGN KEY (post_id) REFERENCES posts(id) ON DELETE CASCADE,
- FOREIGN KEY (tag_id) REFERENCES tags(id) ON DELETE CASCADE
-) ENGINE=InnoDB COMMENT='帖子标签关联表';
-
--- 用户行为表
-CREATE TABLE behaviors (
- id BIGINT AUTO_INCREMENT PRIMARY KEY COMMENT '行为ID',
- user_id INT NOT NULL COMMENT '用户ID',
- post_id INT NOT NULL COMMENT '帖子ID',
- type ENUM('like', 'comment', 'favorite', 'view', 'share') NOT NULL COMMENT '行为类型',
- value INT DEFAULT 1 COMMENT '行为值',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '行为时间',
- FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE,
- FOREIGN KEY (post_id) REFERENCES posts(id) ON DELETE CASCADE
-) ENGINE=InnoDB COMMENT='用户行为记录表';
-
--- 评论表
-CREATE TABLE comments (
- id INT AUTO_INCREMENT PRIMARY KEY COMMENT '评论ID',
- post_id INT NOT NULL COMMENT '帖子ID',
- user_id INT NOT NULL COMMENT '用户ID',
- parent_id INT DEFAULT NULL COMMENT '父评论ID',
- content TEXT NOT NULL COMMENT '评论内容',
- status ENUM('active', 'deleted') DEFAULT 'active' COMMENT '状态',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
- updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
- FOREIGN KEY (post_id) REFERENCES posts(id) ON DELETE CASCADE,
- FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE,
- FOREIGN KEY (parent_id) REFERENCES comments(id) ON DELETE CASCADE
-) ENGINE=InnoDB COMMENT='评论表';
-
--- 用户关注关系表
-CREATE TABLE follows (
- follower_id INT NOT NULL COMMENT '关注者ID',
- followee_id INT NOT NULL COMMENT '被关注者ID',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '关注时间',
- PRIMARY KEY (follower_id, followee_id),
- FOREIGN KEY (follower_id) REFERENCES users(id) ON DELETE CASCADE,
- FOREIGN KEY (followee_id) REFERENCES users(id) ON DELETE CASCADE
-) ENGINE=InnoDB COMMENT='用户关注关系表';
-
--- 通知表
-CREATE TABLE notifications (
- id INT AUTO_INCREMENT PRIMARY KEY COMMENT '通知ID',
- user_id INT NOT NULL COMMENT '接收用户ID',
- type ENUM('like', 'comment', 'follow', 'system', 'audit') NOT NULL COMMENT '通知类型',
- content JSON NOT NULL COMMENT '通知内容',
- is_read BOOLEAN DEFAULT FALSE COMMENT '是否已读',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
- FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE
-) ENGINE=InnoDB COMMENT='用户通知表';
-
--- 审核记录表
-CREATE TABLE audits (
- id INT AUTO_INCREMENT PRIMARY KEY COMMENT '审核ID',
- post_id INT NOT NULL COMMENT '帖子ID',
- admin_id INT NOT NULL COMMENT '管理员ID',
- result ENUM('approved', 'rejected') NOT NULL COMMENT '审核结果',
- reason VARCHAR(255) COMMENT '审核原因',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '审核时间',
- FOREIGN KEY (post_id) REFERENCES posts(id) ON DELETE CASCADE,
- FOREIGN KEY (admin_id) REFERENCES users(id) ON DELETE CASCADE
-) ENGINE=InnoDB COMMENT='内容审核记录表';
-
--- 日志表
-CREATE TABLE logs (
- id BIGINT AUTO_INCREMENT PRIMARY KEY COMMENT '日志ID',
- user_id INT DEFAULT NULL COMMENT '用户ID',
- type ENUM('access', 'error', 'behavior', 'system') NOT NULL COMMENT '日志类型',
- content TEXT NOT NULL COMMENT '日志内容',
- ip VARCHAR(45) COMMENT 'IP地址',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '记录时间',
- FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE SET NULL
-) ENGINE=InnoDB COMMENT='系统日志表';
-
--- 用户兴趣标签表(用户画像)
-CREATE TABLE user_tags (
- user_id INT NOT NULL COMMENT '用户ID',
- tag_id INT NOT NULL COMMENT '标签ID',
- weight FLOAT DEFAULT 1.0 COMMENT '兴趣权重',
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
- updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
- PRIMARY KEY (user_id, tag_id),
- FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE,
- FOREIGN KEY (tag_id) REFERENCES tags(id) ON DELETE CASCADE
-) ENGINE=InnoDB COMMENT='用户兴趣标签表';
-
--- 索引优化
-CREATE INDEX idx_posts_heat ON posts(heat);
-CREATE INDEX idx_behaviors_type ON behaviors(type);
-CREATE INDEX idx_notifications_read ON notifications(is_read);
-CREATE INDEX idx_logs_created ON logs(created_at);
-CREATE INDEX idx_comments_post ON comments(post_id);
\ No newline at end of file
diff --git a/API/API-TRM/xiaohongshu-upload-platform/README.md b/API/API-TRM/xiaohongshu-upload-platform/README.md
deleted file mode 100644
index 6f35930..0000000
--- a/API/API-TRM/xiaohongshu-upload-platform/README.md
+++ /dev/null
@@ -1,185 +0,0 @@
-# 小红书内容创作平台
-
-这是一个基于 React + Vite 构建的小红书内容创作平台界面,完全复制了小红书官方创作服务平台的设计和功能。
-
-## 功能特性 ✨
-
-### 🎨 界面设计
-- **完全还原小红书官方设计**:精确复制了小红书创作服务平台的视觉风格
-- **响应式布局**:支持桌面端和移动端适配
-- **现代化UI**:使用 Lucide React 图标库,提供清晰美观的界面
-
-### 📤 上传功能
-- **双模式上传**:支持图片上传和视频上传两种模式
-- **拖拽上传**:支持文件拖拽到上传区域
-- **点击上传**:点击按钮选择文件上传
-- **文件验证**:
- - 图片:支持 JPEG、JPG、PNG、WebP 格式,最大 32MB
- - 视频:支持 MP4、MOV、AVI 格式,最大 2GB
-- **实时进度显示**:带有动画效果的上传进度条
-
-### 🖼️ 文件管理
-- **文件预览**:上传后实时显示文件缩略图
-- **文件信息**:显示文件名、大小等详细信息
-- **批量管理**:支持单个删除和批量清除
-- **文件计数**:实时显示已上传文件数量
-
-### 🎯 交互体验
-- **拖拽反馈**:拖拽时提供视觉反馈效果
-- **加载状态**:上传过程中的加载动画
-- **操作提示**:完成上传后的成功提示
-- **悬停效果**:按钮和文件项的悬停交互
-
-### 🗂️ 导航系统
-- **侧边栏导航**:完整的功能菜单
-- **可展开子菜单**:数据看板等功能的子选项
-- **活跃状态**:当前选中页面的高亮显示
-- **固定布局**:头部和侧边栏固定定位
-
-## 技术栈 🛠️
-
-- **前端框架**:React 19.1.0
-- **构建工具**:Vite 6.0.5
-- **图标库**:Lucide React 0.468.0
-- **样式**:纯 CSS(无预处理器)
-- **开发语言**:JavaScript + JSX
-
-## 安装运行 🚀
-
-1. **安装依赖**
- ```bash
- npm install
- ```
-
-2. **启动开发服务器**
- ```bash
- npm run dev
- ```
-
-3. **打开浏览器**
- ```
- http://localhost:5173
- ```
-
-4. **构建生产版本**
- ```bash
- npm run build
- ```
-
-## 项目结构 📁
-
-```
-发布页面/
-├── public/ # 静态资源
-│ └── vite.svg # Vite 图标
-├── src/
-│ ├── App.jsx # 主应用组件
-│ ├── App.css # 主样式文件
-│ ├── index.css # 全局样式
-│ └── main.jsx # 应用入口
-├── index.html # HTML 入口文件
-├── package.json # 项目配置
-├── vite.config.js # Vite 配置
-└── README.md # 项目说明
-```
-
-## 核心功能实现 💡
-
-### 文件上传处理
-```javascript
-const handleFileUpload = () => {
- const input = document.createElement('input')
- input.type = 'file'
- input.accept = activeTab === 'video' ? 'video/*' : 'image/*'
- input.multiple = activeTab === 'image'
-
- input.onchange = (e) => {
- const files = Array.from(e.target.files)
- if (files.length > 0 && validateFiles(files)) {
- simulateUpload(files)
- }
- }
-
- input.click()
-}
-```
-
-### 拖拽上传实现
-```javascript
-const handleDrop = (e) => {
- e.preventDefault()
- e.stopPropagation()
- setIsDragOver(false)
-
- const files = Array.from(e.dataTransfer.files)
- if (files.length > 0 && validateFiles(files)) {
- simulateUpload(files)
- }
-}
-```
-
-### 文件验证机制
-```javascript
-const validateFiles = (files) => {
- const validImageTypes = ['image/jpeg', 'image/jpg', 'image/png', 'image/webp']
- const validVideoTypes = ['video/mp4', 'video/mov', 'video/avi']
-
- const validTypes = activeTab === 'video' ? validVideoTypes : validImageTypes
- const maxSize = activeTab === 'video' ? 2 * 1024 * 1024 * 1024 : 32 * 1024 * 1024
-
- return files.every(file =>
- validTypes.includes(file.type) && file.size <= maxSize
- )
-}
-```
-
-## 样式特色 🎨
-
-### 响应式设计
-- 桌面端:固定侧边栏布局
-- 移动端:隐藏侧边栏,堆叠布局
-- 自适应文件网格:根据屏幕大小调整列数
-
-### 动画效果
-- 拖拽时的放大效果
-- 进度条的流光动画
-- 文件项的悬停过渡
-- 页面切换的淡入效果
-
-### 色彩方案
-- 主色调:#ff4757(小红书红)
-- 背景色:#f5f7fa(浅灰蓝)
-- 文字色:#333(深灰)
-- 边框色:#e8eaed(浅灰)
-
-## 待扩展功能 🔮
-
-- **后端集成**:连接真实的文件上传 API
-- **用户认证**:登录注册功能
-- **内容编辑**:笔记内容编辑器
-- **数据统计**:真实的数据看板功能
-- **社交功能**:评论、点赞等互动功能
-
-## 开发说明 📝
-
-这个项目完全基于前端实现,所有的上传功能都是模拟的。文件预览使用了 `URL.createObjectURL()` 来生成本地预览链接。在实际部署时,需要:
-
-1. 集成后端文件上传 API
-2. 实现用户认证系统
-3. 添加数据持久化
-4. 优化性能和安全性
-
-## 浏览器兼容性 🌐
-
-- Chrome 90+
-- Firefox 88+
-- Safari 14+
-- Edge 90+
-
-## 许可证 📄
-
-MIT License
-
----
-
-**注意**:本项目仅用于学习和演示目的,请遵守相关法律法规和平台使用条款。
diff --git a/API/API-TRM/xiaohongshu-upload-platform/index.html b/API/API-TRM/xiaohongshu-upload-platform/index.html
deleted file mode 100644
index b919940..0000000
--- a/API/API-TRM/xiaohongshu-upload-platform/index.html
+++ /dev/null
@@ -1,13 +0,0 @@
-<!doctype html>
-<html lang="zh-CN">
- <head>
- <meta charset="UTF-8" />
- <link rel="icon" type="image/svg+xml" href="/vite.svg" />
- <meta name="viewport" content="width=device-width, initial-scale=1.0" />
- <title>小红书创作服务平台</title>
- </head>
- <body>
- <div id="root"></div>
- <script type="module" src="/src/main.jsx"></script>
- </body>
-</html>
diff --git a/API/API-TRM/xiaohongshu-upload-platform/package.json b/API/API-TRM/xiaohongshu-upload-platform/package.json
deleted file mode 100644
index 00a233f..0000000
--- a/API/API-TRM/xiaohongshu-upload-platform/package.json
+++ /dev/null
@@ -1,20 +0,0 @@
-{
- "name": "xiaohongshu-creator-platform",
- "private": true,
- "version": "0.0.0",
- "type": "module",
- "scripts": {
- "dev": "vite",
- "build": "vite build",
- "preview": "vite preview"
- },
- "dependencies": {
- "react": "^18.3.1",
- "react-dom": "^18.3.1",
- "lucide-react": "^0.468.0"
- },
- "devDependencies": {
- "@vitejs/plugin-react": "^4.3.4",
- "vite": "^6.0.5"
- }
-}
diff --git a/API/API-TRM/xiaohongshu-upload-platform/public/vite.svg b/API/API-TRM/xiaohongshu-upload-platform/public/vite.svg
deleted file mode 100644
index ee9fada..0000000
--- a/API/API-TRM/xiaohongshu-upload-platform/public/vite.svg
+++ /dev/null
@@ -1 +0,0 @@
-<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" aria-hidden="true" role="img" class="iconify iconify--logos" width="31.88" height="32" preserveAspectRatio="xMidYMid meet" viewBox="0 0 256 257"><defs><linearGradient id="IconifyId1813088fe1fbc01fb466" x1="-.828%" x2="57.636%" y1="7.652%" y2="78.411%"><stop offset="0%" stop-color="#41D1FF"></stop><stop offset="100%" stop-color="#BD34FE"></stop></linearGradient><linearGradient id="IconifyId1813088fe1fbc01fb467" x1="43.376%" x2="50.316%" y1="2.242%" y2="89.03%"><stop offset="0%" stop-color="#FFEA83"></stop><stop offset="8.333%" stop-color="#FFDD35"></stop><stop offset="100%" stop-color="#FFA800"></stop></linearGradient></defs><path fill="url(#IconifyId1813088fe1fbc01fb466)" d="M255.153 37.938L134.897 252.976c-2.483 4.44-8.862 4.466-11.382.048L.875 37.958c-2.746-4.814 1.371-10.646 6.827-9.67l120.385 21.517a6.537 6.537 0 0 0 2.322-.004l117.867-21.483c5.438-.991 9.574 4.796 6.877 9.62Z"></path><path fill="url(#IconifyId1813088fe1fbc01fb467)" d="M185.432.063L96.44 17.501a3.268 3.268 0 0 0-2.634 3.014l-5.474 92.456a3.268 3.268 0 0 0 3.997 3.378l24.777-5.718c2.318-.535 4.413 1.507 3.936 3.838l-7.361 36.047c-.495 2.426 1.782 4.5 4.151 3.78l15.304-4.649c2.372-.72 4.652 1.36 4.15 3.788l-11.698 56.621c-.732 3.542 3.979 5.473 5.943 2.437l1.313-2.028l72.516-144.72c1.215-2.423-.88-5.186-3.54-4.672l-25.505 4.922c-2.396.462-4.435-1.77-3.759-4.114l16.646-57.705c.677-2.35-1.37-4.583-3.769-4.113Z"></path></svg>
diff --git a/API/API-TRM/xiaohongshu-upload-platform/src/App.css b/API/API-TRM/xiaohongshu-upload-platform/src/App.css
deleted file mode 100644
index 00d10d6..0000000
--- a/API/API-TRM/xiaohongshu-upload-platform/src/App.css
+++ /dev/null
@@ -1,583 +0,0 @@
-.app {
- display: flex;
- min-height: 100vh;
- background-color: #f5f7fa;
-}
-
-/* Header */
-.header {
- position: fixed;
- top: 0;
- left: 0;
- right: 0;
- height: 60px;
- background: #fff;
- border-bottom: 1px solid #e8eaed;
- display: flex;
- align-items: center;
- padding: 0 20px;
- z-index: 1000;
- box-shadow: 0 1px 3px rgba(0, 0, 0, 0.1);
-}
-
-.header-left {
- display: flex;
- align-items: center;
- gap: 12px;
-}
-
-.logo {
- background: #ff4757;
- color: white;
- padding: 6px 12px;
- border-radius: 6px;
- font-size: 14px;
- font-weight: bold;
-}
-
-.header-title {
- font-size: 18px;
- font-weight: 500;
- color: #333;
-}
-
-.header-right {
- margin-left: auto;
- display: flex;
- align-items: center;
- gap: 12px;
-}
-
-.user-info {
- display: flex;
- align-items: center;
- gap: 8px;
- color: #666;
- font-size: 14px;
-}
-
-/* Sidebar */
-.sidebar {
- position: fixed;
- left: 0;
- top: 60px;
- width: 200px;
- height: calc(100vh - 60px);
- background: #fff;
- border-right: 1px solid #e8eaed;
- overflow-y: auto;
- z-index: 999;
-}
-
-.publish-btn {
- margin: 16px;
- background: #ff4757;
- color: white;
- padding: 10px 16px;
- border-radius: 6px;
- font-size: 14px;
- font-weight: 500;
- text-align: center;
- transition: background 0.2s;
-}
-
-.publish-btn:hover {
- background: #ff3742;
-}
-
-.nav-menu {
- padding: 0;
- list-style: none;
-}
-
-.nav-item {
- border-bottom: 1px solid #f0f0f0;
-}
-
-.nav-link {
- display: flex;
- align-items: center;
- padding: 12px 20px;
- color: #333;
- font-size: 14px;
- transition: all 0.2s;
- gap: 8px;
-}
-
-.nav-link:hover {
- background: #f8f9fa;
- color: #ff4757;
-}
-
-.nav-link.active {
- background: linear-gradient(135deg, #ff4757, #ff6b7a);
- color: white;
- font-weight: 500;
-}
-
-.nav-link.active .lucide {
- color: white;
-}
-
-.nav-submenu {
- padding-left: 20px;
- background: #fafafa;
-}
-
-.nav-submenu .nav-link {
- padding: 8px 20px;
- font-size: 13px;
- color: #666;
-}
-
-.nav-submenu .nav-link:hover {
- color: #ff4757;
-}
-
-/* Main Content */
-.main-content {
- margin-left: 200px;
- padding-top: 60px;
- flex: 1;
- min-height: 100vh;
-}
-
-.content-wrapper {
- padding: 20px;
- max-width: 1200px;
- margin: 0 auto;
-}
-
-/* Upload Area */
-.upload-tabs {
- display: flex;
- gap: 20px;
- margin-bottom: 30px;
- border-bottom: 1px solid #e8eaed;
-}
-
-.upload-tab {
- padding: 12px 0;
- font-size: 16px;
- color: #666;
- cursor: pointer;
- border-bottom: 2px solid transparent;
- transition: all 0.2s;
-}
-
-.upload-tab.active {
- color: #ff4757;
- border-bottom-color: #ff4757;
- font-weight: 500;
-}
-
-.upload-area {
- background: #fff;
- border-radius: 8px;
- padding: 80px 40px;
- text-align: center;
- border: 2px dashed #ddd;
- margin-bottom: 40px;
- transition: all 0.2s;
- min-height: 300px;
- display: flex;
- flex-direction: column;
- justify-content: center;
- align-items: center;
- position: relative;
-}
-
-.upload-area:hover {
- border-color: #ff4757;
- background: #fff8f8;
-}
-
-.upload-area.drag-over {
- border-color: #ff4757;
- background: #fff0f0;
- transform: scale(1.02);
-}
-
-.upload-icon {
- width: 100px;
- height: 100px;
- margin: 0 auto 30px;
- background: #f8f9fa;
- border-radius: 50%;
- display: flex;
- align-items: center;
- justify-content: center;
- font-size: 40px;
- color: #ccc;
- transition: all 0.3s ease;
-}
-
-.upload-area:hover .upload-icon {
- background: #ff475710;
- color: #ff4757;
- transform: scale(1.1);
-}
-
-.upload-area.drag-over .upload-icon {
- background: #ff475720;
- color: #ff4757;
- transform: scale(1.2);
-}
-
-.upload-title {
- font-size: 20px;
- color: #333;
- margin-bottom: 12px;
- font-weight: 500;
-}
-
-.upload-subtitle {
- font-size: 14px;
- color: #999;
- margin-bottom: 30px;
-}
-
-.upload-btn {
- background: #ff4757;
- color: white;
- padding: 14px 28px;
- border-radius: 6px;
- font-size: 16px;
- font-weight: 500;
- transition: background 0.2s;
- min-width: 120px;
-}
-
-.upload-btn:hover:not(:disabled) {
- background: #ff3742;
-}
-
-.upload-btn:disabled {
- background: #ccc;
- cursor: not-allowed;
-}
-
-.upload-btn.uploading {
- background: #ff4757;
- opacity: 0.8;
-}
-
-/* File Preview */
-.file-preview-area {
- background: #fff;
- border-radius: 8px;
- padding: 20px;
- margin-bottom: 40px;
- border: 1px solid #e8eaed;
-}
-
-/* Preview Header */
-.preview-header {
- display: flex;
- justify-content: space-between;
- align-items: center;
- margin-bottom: 16px;
-}
-
-.preview-title {
- font-size: 16px;
- color: #333;
- margin-bottom: 16px;
- font-weight: 500;
-}
-
-.clear-files-btn {
- background: #ff4757;
- color: white;
- padding: 6px 12px;
- border-radius: 4px;
- font-size: 12px;
- transition: background 0.2s;
-}
-
-.clear-files-btn:hover {
- background: #ff3742;
-}
-
-.file-grid {
- display: grid;
- grid-template-columns: repeat(auto-fill, minmax(120px, 1fr));
- gap: 16px;
-}
-
-.file-item {
- display: flex;
- flex-direction: column;
- align-items: center;
- padding: 12px;
- border: 1px solid #f0f0f0;
- border-radius: 6px;
- transition: all 0.2s ease;
- position: relative;
-}
-
-.file-item:hover {
- border-color: #ff4757;
- box-shadow: 0 2px 8px rgba(255, 71, 87, 0.1);
-}
-
-.file-item:hover .remove-file-btn {
- opacity: 1;
-}
-
-.remove-file-btn {
- position: absolute;
- top: 4px;
- right: 4px;
- background: rgba(255, 71, 87, 0.8);
- color: white;
- border-radius: 50%;
- width: 20px;
- height: 20px;
- display: flex;
- align-items: center;
- justify-content: center;
- font-size: 14px;
- font-weight: bold;
- opacity: 0;
- transition: all 0.2s;
-}
-
-.file-thumbnail {
- width: 80px;
- height: 80px;
- border-radius: 6px;
- overflow: hidden;
- margin-bottom: 8px;
- display: flex;
- align-items: center;
- justify-content: center;
- background: #f8f9fa;
-}
-
-.file-thumbnail img {
- width: 100%;
- height: 100%;
- object-fit: cover;
-}
-
-.video-thumbnail {
- color: #666;
-}
-
-.file-info {
- text-align: center;
- width: 100%;
-}
-
-.file-name {
- font-size: 12px;
- color: #333;
- margin-bottom: 4px;
- font-weight: 500;
-}
-
-.file-size {
- font-size: 11px;
- color: #999;
-}
-
-/* Upload Progress */
-.progress-container {
- margin-top: 20px;
- width: 100%;
- max-width: 400px;
-}
-
-.progress-bar {
- width: 100%;
- height: 8px;
- background-color: #f0f0f0;
- border-radius: 4px;
- overflow: hidden;
- margin-bottom: 8px;
-}
-
-.progress-fill {
- height: 100%;
- background: linear-gradient(90deg, #ff4757, #ff6b7a);
- border-radius: 4px;
- transition: width 0.3s ease;
- position: relative;
-}
-
-.progress-fill::after {
- content: '';
- position: absolute;
- top: 0;
- left: 0;
- right: 0;
- bottom: 0;
- background: linear-gradient(90deg, transparent, rgba(255, 255, 255, 0.3), transparent);
- animation: shimmer 1.5s infinite;
-}
-
-@keyframes shimmer {
- 0% { transform: translateX(-100%); }
- 100% { transform: translateX(100%); }
-}
-
-.progress-text {
- text-align: center;
- font-size: 12px;
- color: #666;
- font-weight: 500;
-}
-
-/* Upload Info */
-.upload-info {
- display: flex;
- gap: 60px;
- justify-content: center;
- margin-top: 40px;
- padding: 20px;
- opacity: 1;
- transition: opacity 0.3s ease;
-}
-
-.upload-info.fade-in {
- animation: fadeIn 0.3s ease-in-out;
-}
-
-@keyframes fadeIn {
- from {
- opacity: 0;
- transform: translateY(10px);
- }
- to {
- opacity: 1;
- transform: translateY(0);
- }
-}
-
-.info-item {
- text-align: center;
- flex: 1;
- max-width: 300px;
-}
-
-.info-title {
- font-size: 16px;
- color: #333;
- margin-bottom: 12px;
- font-weight: 500;
-}
-
-.info-desc {
- font-size: 13px;
- color: #666;
- line-height: 1.6;
-}
-
-/* Page Content Styles */
-.page-content {
- padding: 40px;
- background: white;
- border-radius: 12px;
- box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
- margin: 20px 0;
- min-height: 500px;
-}
-
-.page-header {
- margin-bottom: 40px;
- padding-bottom: 20px;
- border-bottom: 1px solid #e8eaed;
-}
-
-.page-title {
- font-size: 24px;
- font-weight: 600;
- color: #333;
- margin: 0;
-}
-
-.page-body {
- display: flex;
- align-items: center;
- justify-content: center;
- min-height: 400px;
-}
-
-.placeholder-content {
- text-align: center;
- max-width: 400px;
-}
-
-.placeholder-icon {
- color: #ff4757;
- margin-bottom: 20px;
- display: flex;
- justify-content: center;
-}
-
-.placeholder-title {
- font-size: 20px;
- font-weight: 500;
- color: #333;
- margin: 0 0 15px 0;
-}
-
-.placeholder-desc {
- font-size: 14px;
- color: #666;
- line-height: 1.6;
- margin: 0;
-}
-
-/* Responsive */
-@media (max-width: 768px) {
- .sidebar {
- transform: translateX(-100%);
- transition: transform 0.3s;
- }
-
- .main-content {
- margin-left: 0;
- }
-
- .header-title {
- display: none;
- }
-
- .upload-area {
- padding: 60px 20px;
- margin: 0 10px 30px;
- }
-
- .upload-info {
- flex-direction: column;
- gap: 30px;
- padding: 10px;
- }
-
- .content-wrapper {
- padding: 15px;
- }
-
- .upload-tabs {
- gap: 15px;
- }
-
- .page-content {
- padding: 20px;
- margin: 10px;
- }
-
- .page-title {
- font-size: 20px;
- }
-
- .placeholder-title {
- font-size: 18px;
- }
-
- .placeholder-desc {
- font-size: 13px;
- }
-}
diff --git a/API/API-TRM/xiaohongshu-upload-platform/src/App.jsx b/API/API-TRM/xiaohongshu-upload-platform/src/App.jsx
deleted file mode 100644
index 8388b7b..0000000
--- a/API/API-TRM/xiaohongshu-upload-platform/src/App.jsx
+++ /dev/null
@@ -1,410 +0,0 @@
-import React, { useState } from 'react'
-import {
- Home,
- Settings,
- BarChart3,
- PieChart,
- TrendingUp,
- Activity,
- BookOpen,
- Users,
- Upload,
- Image,
- Video,
- ChevronDown,
- User
-} from 'lucide-react'
-import './App.css'
-
-function App() {
- const [activeTab, setActiveTab] = useState('image')
- const [expandedMenu, setExpandedMenu] = useState('dashboard')
- const [activePage, setActivePage] = useState('dashboard') // 新增:当前激活的页面
- const [isDragOver, setIsDragOver] = useState(false)
- const [isUploading, setIsUploading] = useState(false)
- const [uploadedFiles, setUploadedFiles] = useState([])
- const [uploadProgress, setUploadProgress] = useState(0)
-
- const validateFiles = (files) => {
- const validImageTypes = ['image/jpeg', 'image/jpg', 'image/png', 'image/webp']
- const validVideoTypes = ['video/mp4', 'video/mov', 'video/avi']
-
- const validTypes = activeTab === 'video' ? validVideoTypes : validImageTypes
- const maxSize = activeTab === 'video' ? 2 * 1024 * 1024 * 1024 : 32 * 1024 * 1024 // 2GB for video, 32MB for images
-
- const invalidFiles = files.filter(file => {
- return !validTypes.includes(file.type) || file.size > maxSize
- })
-
- if (invalidFiles.length > 0) {
- alert(`发现 ${invalidFiles.length} 个无效文件,请检查文件格式和大小`)
- return false
- }
-
- return true
- }
-
- const simulateUpload = (files) => {
- setIsUploading(true)
- setUploadProgress(0)
- setUploadedFiles(files)
-
- // 模拟上传进度
- const interval = setInterval(() => {
- setUploadProgress(prev => {
- if (prev >= 100) {
- clearInterval(interval)
- setIsUploading(false)
- alert(`成功上传了 ${files.length} 个文件`)
- return 100
- }
- return prev + 10
- })
- }, 200)
- }
-
- const handleFileUpload = () => {
- if (isUploading) return
-
- const input = document.createElement('input')
- input.type = 'file'
- input.accept = activeTab === 'video' ? 'video/*' : 'image/*'
- input.multiple = activeTab === 'image'
- input.onchange = (e) => {
- const files = Array.from(e.target.files)
- if (files.length > 0 && validateFiles(files)) {
- simulateUpload(files)
- }
- }
- input.click()
- }
-
- const handleDragOver = (e) => {
- e.preventDefault()
- e.stopPropagation()
- setIsDragOver(true)
- }
-
- const handleDragLeave = (e) => {
- e.preventDefault()
- e.stopPropagation()
- setIsDragOver(false)
- }
-
- const handleDrop = (e) => {
- e.preventDefault()
- e.stopPropagation()
- setIsDragOver(false)
-
- if (isUploading) return
-
- const files = Array.from(e.dataTransfer.files)
- if (files.length > 0 && validateFiles(files)) {
- simulateUpload(files)
- }
- }
-
- const clearUploadedFiles = () => {
- setUploadedFiles([])
- }
-
- const removeFile = (indexToRemove) => {
- setUploadedFiles(prev => prev.filter((_, index) => index !== indexToRemove))
- }
-
- const menuItems = [
- { id: 'home', label: '首页', icon: Home },
- { id: 'notebooks', label: '笔记管理', icon: BookOpen },
- {
- id: 'dashboard',
- label: '数据看板',
- icon: BarChart3,
- submenu: [
- { id: 'overview', label: '账号概况' },
- { id: 'content', label: '内容分析' },
- { id: 'fans', label: '粉丝数据' }
- ]
- },
- { id: 'activity', label: '活动中心', icon: Activity },
- { id: 'notes', label: '笔记灵感', icon: BookOpen },
- { id: 'creator', label: '创作学院', icon: Users },
- { id: 'journal', label: '创作日刊', icon: BookOpen }
- ]
- const toggleMenu = (menuId) => {
- setExpandedMenu(expandedMenu === menuId ? null : menuId)
- }
-
- // 新增:处理页面切换的函数
- const handlePageChange = (pageId) => {
- setActivePage(pageId)
- // 如果点击的是有子菜单的项目,也要展开子菜单
- const menuItem = menuItems.find(item => item.id === pageId)
- if (menuItem && menuItem.submenu) {
- setExpandedMenu(pageId)
- }
- }
-
- return (
- <div className="app">
- {/* Header */}
- <header className="header">
- <div className="header-left">
- <div className="logo">小红书</div>
- <h1 className="header-title">创作服务平台</h1>
- </div>
- <div className="header-right">
- <div className="user-info">
- <User size={16} />
- <span>小红薯63081EA1</span>
- </div>
- </div>
- </header>
-
- {/* Sidebar */}
- <aside className="sidebar">
- <button className="publish-btn">发布笔记</button>
- <nav className="nav-menu">
- {menuItems.map((item) => (
- <div key={item.id} className="nav-item">
- <a
- href="#"
- className={`nav-link ${activePage === item.id ? 'active' : ''}`}
- onClick={(e) => {
- e.preventDefault()
- if (item.submenu) {
- toggleMenu(item.id)
- } else {
- handlePageChange(item.id)
- }
- }}
- >
- <item.icon size={16} />
- <span>{item.label}</span>
- {item.submenu && <ChevronDown size={16} style={{ marginLeft: 'auto', transform: expandedMenu === item.id ? 'rotate(180deg)' : 'rotate(0deg)', transition: 'transform 0.3s ease' }} />}
- </a>
-
- {item.submenu && expandedMenu === item.id && (
- <div className="nav-submenu">
- {item.submenu.map((subItem) => (
- <a
- key={subItem.id}
- href="#"
- className={`nav-link ${activePage === subItem.id ? 'active' : ''}`}
- onClick={(e) => {
- e.preventDefault()
- handlePageChange(subItem.id)
- }}
- >
- {subItem.label}
- </a>
- ))}
- </div>
- )}
- </div>
- ))}
- </nav>
- </aside> {/* Main Content */}
- <main className="main-content">
- <div className="content-wrapper">
- {activePage === 'dashboard' || activePage === 'overview' || activePage === 'content' || activePage === 'fans' ? (
- // 上传页面内容(数据看板相关页面显示上传功能)
- <>
- {/* Upload Tabs */}
- <div className="upload-tabs">
- <button
- className={`upload-tab ${activeTab === 'video' ? 'active' : ''}`}
- onClick={() => setActiveTab('video')}
- >
- 上传视频
- </button>
- <button
- className={`upload-tab ${activeTab === 'image' ? 'active' : ''}`}
- onClick={() => setActiveTab('image')}
- >
- 上传图文
- </button>
- </div>
-
- {/* Upload Area */}
- <div
- className={`upload-area ${isDragOver ? 'drag-over' : ''}`}
- onDragOver={handleDragOver}
- onDragLeave={handleDragLeave}
- onDrop={handleDrop}
- >
- <div className="upload-icon">
- {activeTab === 'video' ? <Video /> : <Image />}
- </div>
- <h2 className="upload-title">
- {activeTab === 'video' ? '拖拽视频到此处或点击上传' : '拖拽图片到此处或点击上传'}
- </h2>
- <p className="upload-subtitle">
- {activeTab === 'video' ? '(需支持上传格式)' : '(需支持上传格式)'}
- </p>
- <button
- className={`upload-btn ${isUploading ? 'uploading' : ''}`}
- onClick={handleFileUpload}
- disabled={isUploading}
- >
- {isUploading ? `上传中... ${uploadProgress}%` : (activeTab === 'video' ? '上传视频' : '上传图片')}
- </button>
-
- {/* Upload Progress Bar */}
- {isUploading && (
- <div className="progress-container">
- <div className="progress-bar">
- <div
- className="progress-fill"
- style={{ width: `${uploadProgress}%` }}
- ></div>
- </div>
- <div className="progress-text">{uploadProgress}%</div>
- </div>
- )}
- </div>
-
- {/* File Preview Area */}
- {uploadedFiles.length > 0 && (
- <div className="file-preview-area">
- <div className="preview-header">
- <h3 className="preview-title">已上传文件 ({uploadedFiles.length})</h3>
- <button className="clear-files-btn" onClick={clearUploadedFiles}>
- 清除所有
- </button>
- </div>
- <div className="file-grid">
- {uploadedFiles.map((file, index) => (
- <div key={index} className="file-item">
- <button
- className="remove-file-btn"
- onClick={() => removeFile(index)}
- title="删除文件"
- >
- ×
- </button>
- {file.type?.startsWith('image/') ? (
- <div className="file-thumbnail">
- <img src={URL.createObjectURL(file)} alt={file.name} />
- </div>
- ) : (
- <div className="file-thumbnail video-thumbnail">
- <Video size={24} />
- </div>
- )}
- <div className="file-info">
- <div className="file-name" title={file.name}>
- {file.name.length > 20 ? file.name.substring(0, 17) + '...' : file.name}
- </div>
- <div className="file-size">
- {(file.size / 1024 / 1024).toFixed(2)} MB
- </div>
- </div>
- </div>
- ))}
- </div>
- </div>
- )}
-
- {/* Upload Info */}
- <div className="upload-info fade-in" key={activeTab}>
- {activeTab === 'image' ? (
- <>
- <div className="info-item">
- <h3 className="info-title">图片大小</h3>
- <p className="info-desc">
- 支持上传的图片大小,<br />
- 最大32MB的图片文件
- </p>
- </div>
- <div className="info-item">
- <h3 className="info-title">图片格式</h3>
- <p className="info-desc">
- 支持上传的图片格式:<br />
- 推荐使用png、jpg、jpeg、webp,不支持gif、live及其他转化的动图
- </p>
- </div>
- <div className="info-item">
- <h3 className="info-title">图片分辨率</h3>
- <p className="info-desc">
- 不要竖图片尺寸,推荐上传3:4尺寸之间,分辨率不低于720*960的图片,<br />
- 超过17张的时候图片将自动压缩至相配尺寸
- </p>
- </div>
- </>
- ) : (
- <>
- <div className="info-item">
- <h3 className="info-title">视频大小</h3>
- <p className="info-desc">
- 支持种类5分钟内视频,<br />
- 最大2GB的视频文件
- </p>
- </div>
- <div className="info-item">
- <h3 className="info-title">视频格式</h3>
- <p className="info-desc">
- 支持常用视频格式:<br />
- 推荐使用mp4、mov
- </p>
- </div>
- <div className="info-item">
- <h3 className="info-title">视频分辨率</h3>
- <p className="info-desc">
- 推荐上传720P (1280*720) 及以上视频,<br />
- 超过1080P的视频可能可能导致上传稍慢且消耗流量
- </p>
- </div>
- </>
- )}
- </div>
- </>
- ) : (
- // 其他页面的内容
- <div className="page-content">
- <div className="page-header">
- <h1 className="page-title">
- {activePage === 'home' && '首页'}
- {activePage === 'notebooks' && '笔记管理'}
- {activePage === 'activity' && '活动中心'}
- {activePage === 'notes' && '笔记灵感'}
- {activePage === 'creator' && '创作学院'}
- {activePage === 'journal' && '创作日刊'}
- </h1>
- </div>
- <div className="page-body">
- <div className="placeholder-content">
- <div className="placeholder-icon">
- {activePage === 'home' && <Home size={48} />}
- {activePage === 'notebooks' && <BookOpen size={48} />}
- {activePage === 'activity' && <Activity size={48} />}
- {activePage === 'notes' && <BookOpen size={48} />}
- {activePage === 'creator' && <Users size={48} />}
- {activePage === 'journal' && <BookOpen size={48} />}
- </div>
- <h3 className="placeholder-title">
- {activePage === 'home' && '欢迎来到小红书创作平台'}
- {activePage === 'notebooks' && '笔记管理功能开发中'}
- {activePage === 'activity' && '活动中心功能开发中'}
- {activePage === 'notes' && '笔记灵感功能开发中'}
- {activePage === 'creator' && '创作学院功能开发中'}
- {activePage === 'journal' && '创作日刊功能开发中'}
- </h3>
- <p className="placeholder-desc">
- {activePage === 'home' && '在这里您可以管理您的创作内容,查看数据分析,获取创作灵感。'}
- {activePage === 'notebooks' && '这里将显示您的所有笔记,支持编辑、删除、分类等操作。'}
- {activePage === 'activity' && '这里将展示最新的平台活动,让您参与更多有趣的创作活动。'}
- {activePage === 'notes' && '这里将为您提供创作灵感和写作建议,帮助您创作更好的内容。'}
- {activePage === 'creator' && '这里将提供创作技巧教学和平台规则说明,助您成为优秀创作者。'}
- {activePage === 'journal' && '这里将展示创作相关的最新资讯和平台动态。'}
- </p>
- </div>
- </div>
- </div>
- )}
- </div>
- </main>
- </div>
- )
-}
-
-export default App
diff --git a/API/API-TRM/xiaohongshu-upload-platform/src/index.css b/API/API-TRM/xiaohongshu-upload-platform/src/index.css
deleted file mode 100644
index 72c144a..0000000
--- a/API/API-TRM/xiaohongshu-upload-platform/src/index.css
+++ /dev/null
@@ -1,29 +0,0 @@
-* {
- margin: 0;
- padding: 0;
- box-sizing: border-box;
-}
-
-body {
- font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'PingFang SC', 'Hiragino Sans GB', 'Microsoft YaHei', sans-serif;
- -webkit-font-smoothing: antialiased;
- -moz-osx-font-smoothing: grayscale;
- background-color: #f5f7fa;
-}
-
-button {
- border: none;
- background: none;
- cursor: pointer;
- font-family: inherit;
-}
-
-a {
- text-decoration: none;
- color: inherit;
-}
-
-#root {
- width: 100%;
- min-height: 100vh;
-}
diff --git a/API/API-TRM/xiaohongshu-upload-platform/src/main.jsx b/API/API-TRM/xiaohongshu-upload-platform/src/main.jsx
deleted file mode 100644
index b9a1a6d..0000000
--- a/API/API-TRM/xiaohongshu-upload-platform/src/main.jsx
+++ /dev/null
@@ -1,10 +0,0 @@
-import { StrictMode } from 'react'
-import { createRoot } from 'react-dom/client'
-import './index.css'
-import App from './App.jsx'
-
-createRoot(document.getElementById('root')).render(
- <StrictMode>
- <App />
- </StrictMode>,
-)
diff --git a/API/API-TRM/xiaohongshu-upload-platform/vite.config.js b/API/API-TRM/xiaohongshu-upload-platform/vite.config.js
deleted file mode 100644
index 8b0f57b..0000000
--- a/API/API-TRM/xiaohongshu-upload-platform/vite.config.js
+++ /dev/null
@@ -1,7 +0,0 @@
-import { defineConfig } from 'vite'
-import react from '@vitejs/plugin-react'
-
-// https://vite.dev/config/
-export default defineConfig({
- plugins: [react()],
-})
diff --git "a/API/API-TRM/\351\241\271\347\233\256\346\201\242\345\244\215\346\212\245\345\221\212.md" "b/API/API-TRM/\351\241\271\347\233\256\346\201\242\345\244\215\346\212\245\345\221\212.md"
deleted file mode 100644
index 32a335b..0000000
--- "a/API/API-TRM/\351\241\271\347\233\256\346\201\242\345\244\215\346\212\245\345\221\212.md"
+++ /dev/null
@@ -1,105 +0,0 @@
-# 小红书创作平台 - 项目恢复完成 ✅
-
-## 恢复状态
-
-🎉 **项目已完全恢复!**所有代码和功能都已重新创建并正常工作。
-
-## 当前项目包含:
-
-### 📁 文件结构
-```
-e:\api大作业\发布页面/
-├── index.html # HTML入口文件
-├── package.json # 项目配置和依赖
-├── README.md # 详细项目文档
-├── vite.config.js # Vite构建配置
-├── public/
-│ └── vite.svg # Vite图标
-└── src/
- ├── App.css # 主要样式文件
- ├── App.jsx # 主应用组件
- ├── index.css # 全局样式
- └── main.jsx # React应用入口
-```
-
-### 🚀 核心功能
-
-1. **完整的小红书创作平台界面**
- - ✅ 头部导航栏(Logo + 用户信息)
- - ✅ 侧边栏菜单(可展开子菜单)
- - ✅ 上传区域(图片/视频切换)
- - ✅ 文件预览网格
- - ✅ 响应式设计
-
-2. **上传功能**
- - ✅ 拖拽上传
- - ✅ 点击上传
- - ✅ 文件类型验证
- - ✅ 文件大小限制
- - ✅ 上传进度条
- - ✅ 实时预览
-
-3. **文件管理**
- - ✅ 文件缩略图显示
- - ✅ 文件信息展示
- - ✅ 单个文件删除
- - ✅ 批量清除功能
- - ✅ 文件计数
-
-4. **交互体验**
- - ✅ 拖拽视觉反馈
- - ✅ 悬停动画效果
- - ✅ 加载状态显示
- - ✅ 操作成功提示
-
-### 🛠️ 技术栈
-
-- **React 18.3.1** - 前端框架
-- **Vite 6.0.5** - 构建工具
-- **Lucide React 0.468.0** - 图标库
-- **纯CSS** - 样式设计
-
-### 📱 当前状态
-
-- ✅ 依赖安装完成
-- ✅ 开发服务器运行中
-- ✅ 浏览器已打开应用 (http://localhost:5173)
-- ✅ 所有功能正常工作
-- ✅ 无代码错误
-
-### 🎯 功能测试清单
-
-可以测试以下功能:
-
-1. **界面导航**
- - [ ] 点击侧边栏菜单项
- - [ ] 展开/收起数据看板子菜单
- - [ ] 切换上传标签页(图片/视频)
-
-2. **文件上传**
- - [ ] 点击上传按钮选择文件
- - [ ] 拖拽文件到上传区域
- - [ ] 观察上传进度条动画
- - [ ] 查看文件预览效果
-
-3. **文件管理**
- - [ ] 悬停文件项查看删除按钮
- - [ ] 删除单个文件
- - [ ] 清除所有文件
-
-4. **响应式测试**
- - [ ] 调整浏览器窗口大小
- - [ ] 测试移动端适配
-
-### 🔄 后续开发
-
-项目已为API集成做好准备:
-
-1. **替换模拟上传** → 真实API调用
-2. **添加用户认证** → 登录/注册功能
-3. **连接后端数据** → 真实数据存储
-4. **添加路由** → 页面导航功能
-
----
-
-**🎊 恢复完成!项目已经可以正常使用了!**
diff --git a/xiaohongshu-upload-platform/src/ljc/back_end/app.py b/LJC/back_end/app.py
similarity index 96%
rename from xiaohongshu-upload-platform/src/ljc/back_end/app.py
rename to LJC/back_end/app.py
index cb62a4d..08bd864 100644
--- a/xiaohongshu-upload-platform/src/ljc/back_end/app.py
+++ b/LJC/back_end/app.py
@@ -25,6 +25,9 @@
created_at = db.Column(db.TIMESTAMP, server_default=db.func.current_timestamp(), comment='创建时间')
updated_at = db.Column(db.TIMESTAMP, server_default=db.func.current_timestamp(),
onupdate=db.func.current_timestamp(), comment='更新时间')
+ birthday = db.Column(db.TIMESTAMP, server_default=db.func.current_timestamp(),comment='生日')
+ gender = db.Column(db.String(10),comment='性别')
+ location = db.Column(db.String(100),comment='所在地')
# 关系定义
posts = db.relationship('Post', backref='author', lazy=True)
@@ -218,7 +221,10 @@
'bio': user.bio,
'following_count': following_count,
'followers_count': followers_count,
- 'is_following': is_following
+ 'is_following': is_following,
+ 'gender': user.gender,
+ 'location': user.location,
+ 'birthday': user.birthday
})
# 更新用户信息
@@ -233,10 +239,17 @@
return jsonify({'error': 'User not found'}), 404
data = request.json
+ print(data)
if 'avatar' in data:
user.avatar = data['avatar']
if 'bio' in data:
user.bio = data['bio']
+ if 'gender' in data:
+ user.gender = data['gender']
+ if 'location' in data:
+ user.location = data['location']
+ if 'birthday' in data:
+ user.birthday = data['birthday']
db.session.commit()
return jsonify({
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/.gitignore b/LJC/personalpage/.gitignore
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/.gitignore
rename to LJC/personalpage/.gitignore
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/README.md b/LJC/personalpage/README.md
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/README.md
rename to LJC/personalpage/README.md
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/package.json b/LJC/personalpage/package.json
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/package.json
rename to LJC/personalpage/package.json
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/public/favicon.ico b/LJC/personalpage/public/favicon.ico
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/public/favicon.ico
rename to LJC/personalpage/public/favicon.ico
Binary files differ
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/public/index.html b/LJC/personalpage/public/index.html
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/public/index.html
rename to LJC/personalpage/public/index.html
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/public/logo192.png b/LJC/personalpage/public/logo192.png
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/public/logo192.png
rename to LJC/personalpage/public/logo192.png
Binary files differ
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/public/logo512.png b/LJC/personalpage/public/logo512.png
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/public/logo512.png
rename to LJC/personalpage/public/logo512.png
Binary files differ
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/public/manifest.json b/LJC/personalpage/public/manifest.json
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/public/manifest.json
rename to LJC/personalpage/public/manifest.json
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/public/robots.txt b/LJC/personalpage/public/robots.txt
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/public/robots.txt
rename to LJC/personalpage/public/robots.txt
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/App.css b/LJC/personalpage/src/App.css
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/App.css
rename to LJC/personalpage/src/App.css
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/App.js b/LJC/personalpage/src/App.js
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/App.js
rename to LJC/personalpage/src/App.js
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/App.test.js b/LJC/personalpage/src/App.test.js
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/App.test.js
rename to LJC/personalpage/src/App.test.js
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/components/EditProfileForm.jsx b/LJC/personalpage/src/components/EditProfileForm.jsx
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/components/EditProfileForm.jsx
rename to LJC/personalpage/src/components/EditProfileForm.jsx
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/components/FavoritePosts.jsx b/LJC/personalpage/src/components/FavoritePosts.jsx
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/components/FavoritePosts.jsx
rename to LJC/personalpage/src/components/FavoritePosts.jsx
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/components/FollowButton.jsx b/LJC/personalpage/src/components/FollowButton.jsx
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/components/FollowButton.jsx
rename to LJC/personalpage/src/components/FollowButton.jsx
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/components/UserProfile.jsx b/LJC/personalpage/src/components/UserProfile.jsx
similarity index 97%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/components/UserProfile.jsx
rename to LJC/personalpage/src/components/UserProfile.jsx
index ee361de..fe02fa0 100644
--- a/xiaohongshu-upload-platform/src/ljc/personalpage/src/components/UserProfile.jsx
+++ b/LJC/personalpage/src/components/UserProfile.jsx
@@ -1,4 +1,4 @@
-import React, { useState, useEffect } from 'react';
+import React, { useState, useEffect, Profiler } from 'react';
import {
Box,
Grid,
@@ -142,9 +142,9 @@
const [formData, setFormData] = useState({
avatar: '',
bio: '',
- gender: 'female',
- birthday: '1995-05-20',
- location: '上海'
+ gender: '',
+ birthday: '',
+ location: ''
});
// 显示提示信息
@@ -206,9 +206,9 @@
setFormData({
avatar: profileUserRes.data.avatar || '',
bio: profileUserRes.data.bio || '',
- gender: 'female',
- birthday: '1995-05-20',
- location: '上海'
+ gender: profileUserRes.data.gender || '',
+ birthday: profileUserRes.data.birthday || '',
+ location: profileUserRes.data.location || ''
});
// 获取用户帖子
@@ -246,12 +246,13 @@
// 加载关注列表
const followingRes = await getUserFollowing(userId);
setFollowing(followingRes.data);
+ console.log(followingRes.data)
} else if (activeTab === 3) {
// 加载粉丝列表
const followersRes = await getUserFollowers(userId);
//
- setFollowers(followersRes.data);
- console.log(followersRes.data)
+ setFollowers(followersRes.data.data);
+ console.log(followersRes.data.data)
}
} catch (error) {
@@ -357,7 +358,10 @@
setUpdating(true);
const data = {
avatar: formData.avatar,
- bio: formData.bio
+ bio: formData.bio,
+ gender: formData.gender,
+ birthday: formData.birthday,
+ location: formData.location
};
// 调用更新API
@@ -367,6 +371,7 @@
setProfileUser({ ...profileUser, ...updatedUser.data });
setFormData({ ...formData, ...data });
+
showSnackbar('个人资料更新成功');
setIsEditing(false);
@@ -472,7 +477,7 @@
border: '4px solid white',
boxShadow: 3
}}
- src={profileUser.avatar || 'https://randomuser.me/api/portraits/women/12.jpg'}
+ src={profileUser.avatar || 'https://www.8848seo.cn/zb_users/upload/2023/02/20230210092856_68763.jpeg'}
/>
</Badge>
</Grid>
@@ -489,19 +494,19 @@
<Box sx={{ display: 'flex', mt: 1, gap: 1, flexWrap: 'wrap' }}>
<Chip
icon={<LocationOn fontSize="small" />}
- label="上海"
+ label={formData.location}
size="small"
variant="outlined"
/>
<Chip
icon={<Cake fontSize="small" />}
- label="1995-05-20"
+ label={formData.birthday}
size="small"
variant="outlined"
/>
<Chip
icon={<Female fontSize="small" />}
- label="女"
+ label={formData.gender}
size="small"
variant="outlined"
/>
@@ -1006,7 +1011,7 @@
>
<Avatar
sx={{ width: 100, height: 100 }}
- src={formData.avatar || 'https://randomuser.me/api/portraits/women/12.jpg'}
+ src={formData.avatar || 'https://www.8848seo.cn/zb_users/upload/2023/02/20230210092856_68763.jpeg'}
/>
</Badge>
</Box>
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/index.css b/LJC/personalpage/src/index.css
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/index.css
rename to LJC/personalpage/src/index.css
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/index.js b/LJC/personalpage/src/index.js
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/index.js
rename to LJC/personalpage/src/index.js
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/logo.svg b/LJC/personalpage/src/logo.svg
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/logo.svg
rename to LJC/personalpage/src/logo.svg
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/reportWebVitals.js b/LJC/personalpage/src/reportWebVitals.js
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/reportWebVitals.js
rename to LJC/personalpage/src/reportWebVitals.js
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/services/api.js b/LJC/personalpage/src/services/api.js
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/services/api.js
rename to LJC/personalpage/src/services/api.js
diff --git a/xiaohongshu-upload-platform/src/ljc/personalpage/src/setupTests.js b/LJC/personalpage/src/setupTests.js
similarity index 100%
rename from xiaohongshu-upload-platform/src/ljc/personalpage/src/setupTests.js
rename to LJC/personalpage/src/setupTests.js
diff --git a/API/API-TRM/TRM/Back/README.md b/TRM/back/README.md
similarity index 100%
rename from API/API-TRM/TRM/Back/README.md
rename to TRM/back/README.md
diff --git a/API/API-TRM/TRM/Back/__pycache__/__init__.cpython-312.pyc b/TRM/back/__pycache__/__init__.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/TRM/Back/__pycache__/__init__.cpython-312.pyc
rename to TRM/back/__pycache__/__init__.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/TRM/Back/__pycache__/config.cpython-310.pyc b/TRM/back/__pycache__/config.cpython-310.pyc
similarity index 100%
rename from API/API-TRM/TRM/Back/__pycache__/config.cpython-310.pyc
rename to TRM/back/__pycache__/config.cpython-310.pyc
Binary files differ
diff --git a/API/API-TRM/TRM/Back/app.py b/TRM/back/app.py
similarity index 100%
rename from API/API-TRM/TRM/Back/app.py
rename to TRM/back/app.py
diff --git a/API/API-TRM/TRM/Back/app/__init__.py b/TRM/back/app/__init__.py
similarity index 100%
rename from API/API-TRM/TRM/Back/app/__init__.py
rename to TRM/back/app/__init__.py
diff --git a/API/API-TRM/TRM/Back/app/__pycache__/__init__.cpython-310.pyc b/TRM/back/app/__pycache__/__init__.cpython-310.pyc
similarity index 100%
rename from API/API-TRM/TRM/Back/app/__pycache__/__init__.cpython-310.pyc
rename to TRM/back/app/__pycache__/__init__.cpython-310.pyc
Binary files differ
diff --git a/API/API-TRM/TRM/Back/app/__pycache__/__init__.cpython-312.pyc b/TRM/back/app/__pycache__/__init__.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/TRM/Back/app/__pycache__/__init__.cpython-312.pyc
rename to TRM/back/app/__pycache__/__init__.cpython-312.pyc
Binary files differ
diff --git a/TRM/back/app/__pycache__/routes.cpython-310.pyc b/TRM/back/app/__pycache__/routes.cpython-310.pyc
new file mode 100644
index 0000000..3293666
--- /dev/null
+++ b/TRM/back/app/__pycache__/routes.cpython-310.pyc
Binary files differ
diff --git a/API/API-TRM/TRM/Back/app/functions/Fpost.py b/TRM/back/app/functions/Fpost.py
similarity index 74%
rename from API/API-TRM/TRM/Back/app/functions/Fpost.py
rename to TRM/back/app/functions/Fpost.py
index e51cf5c..5651e8b 100644
--- a/API/API-TRM/TRM/Back/app/functions/Fpost.py
+++ b/TRM/back/app/functions/Fpost.py
@@ -20,4 +20,12 @@
return False
if res.role !='superadmin':
return False
+ return True
+
+ def review(self,postid,status):
+ res=self.session.query(post).filter(post.id==postid).first()
+ if not res:
+ return False
+ res.status=status
+ self.session.commit()
return True
\ No newline at end of file
diff --git a/TRM/back/app/functions/__pycache__/Fpost.cpython-310.pyc b/TRM/back/app/functions/__pycache__/Fpost.cpython-310.pyc
new file mode 100644
index 0000000..fe0c6de
--- /dev/null
+++ b/TRM/back/app/functions/__pycache__/Fpost.cpython-310.pyc
Binary files differ
diff --git a/API/API-TRM/TRM/Back/app/models/__init__.py b/TRM/back/app/models/__init__.py
similarity index 100%
rename from API/API-TRM/TRM/Back/app/models/__init__.py
rename to TRM/back/app/models/__init__.py
diff --git a/API/API-TRM/TRM/Back/app/models/__pycache__/__init__.cpython-310.pyc b/TRM/back/app/models/__pycache__/__init__.cpython-310.pyc
similarity index 100%
rename from API/API-TRM/TRM/Back/app/models/__pycache__/__init__.cpython-310.pyc
rename to TRM/back/app/models/__pycache__/__init__.cpython-310.pyc
Binary files differ
diff --git a/API/API-TRM/TRM/Back/app/models/__pycache__/post.cpython-310.pyc b/TRM/back/app/models/__pycache__/post.cpython-310.pyc
similarity index 100%
rename from API/API-TRM/TRM/Back/app/models/__pycache__/post.cpython-310.pyc
rename to TRM/back/app/models/__pycache__/post.cpython-310.pyc
Binary files differ
diff --git a/API/API-TRM/TRM/Back/app/models/__pycache__/topics.cpython-310.pyc b/TRM/back/app/models/__pycache__/topics.cpython-310.pyc
similarity index 100%
rename from API/API-TRM/TRM/Back/app/models/__pycache__/topics.cpython-310.pyc
rename to TRM/back/app/models/__pycache__/topics.cpython-310.pyc
Binary files differ
diff --git a/API/API-TRM/TRM/Back/app/models/__pycache__/users.cpython-310.pyc b/TRM/back/app/models/__pycache__/users.cpython-310.pyc
similarity index 100%
rename from API/API-TRM/TRM/Back/app/models/__pycache__/users.cpython-310.pyc
rename to TRM/back/app/models/__pycache__/users.cpython-310.pyc
Binary files differ
diff --git a/API/API-TRM/TRM/Back/app/models/post.py b/TRM/back/app/models/post.py
similarity index 100%
rename from API/API-TRM/TRM/Back/app/models/post.py
rename to TRM/back/app/models/post.py
diff --git a/API/API-TRM/TRM/Back/app/models/topics.py b/TRM/back/app/models/topics.py
similarity index 100%
rename from API/API-TRM/TRM/Back/app/models/topics.py
rename to TRM/back/app/models/topics.py
diff --git a/API/API-TRM/TRM/Back/app/models/users.py b/TRM/back/app/models/users.py
similarity index 100%
rename from API/API-TRM/TRM/Back/app/models/users.py
rename to TRM/back/app/models/users.py
diff --git a/TRM/back/app/routes.py b/TRM/back/app/routes.py
new file mode 100644
index 0000000..90c9c5c
--- /dev/null
+++ b/TRM/back/app/routes.py
@@ -0,0 +1,63 @@
+from flask import Blueprint, render_template
+from .functions.Fpost import Fpost;
+from sqlalchemy import create_engine
+from sqlalchemy.orm import sessionmaker
+from config import Config
+from flask import jsonify,request
+
+main = Blueprint('main', __name__)
+
+
+@main.route('/apostlist',methods=['POST','GET'])
+def postlist():
+ data=request.get_json()
+ engine=create_engine(Config.SQLURL)
+ SessionLocal = sessionmaker(bind=engine)
+ session = SessionLocal()
+ f=Fpost(session)
+ checres=f.checkid(data['userid'])
+ if(not checres):
+ return jsonify({'status': 'error', 'message': 'Unauthorized'})
+ res=f.getlist()
+ respons=[]
+ for datai in res:
+ respons.append({
+ 'id': datai[0],
+ 'title': datai[1],
+ 'status': datai[2]
+ })
+ return jsonify(respons)
+
+@main.route('/agetpost',methods=['POST','GET'])
+def post():
+ data=request.get_json()
+ engine=create_engine(Config.SQLURL)
+ SessionLocal = sessionmaker(bind=engine)
+ session = SessionLocal()
+ f=Fpost(session)
+ checres=f.checkid(data['userid'])
+ if(not checres):
+ return jsonify({'status': 'error', 'message': 'Unauthorized'})
+ res=f.getpost(data['postid'])
+
+ return jsonify(res.to_dict() if res else {})
+
+@main.route('/areview',methods=['POST','GET'])
+def review():
+ data=request.get_json()
+ engine=create_engine(Config.SQLURL)
+ SessionLocal = sessionmaker(bind=engine)
+ session = SessionLocal()
+ f=Fpost(session)
+ checres=f.checkid(data['userid'])
+ if(not checres):
+ return jsonify({'status': 'error', 'message': 'Unauthorized'})
+
+ res=f.review(data['postid'],data['status'])
+ if not res:
+ return jsonify({'status': 'error', 'message': 'Post not found'})
+
+ return jsonify({'status': 'success', 'message': 'Post reviewed successfully'})
+
+
+
diff --git a/API/API-TRM/TRM/Back/app/templates/base.html b/TRM/back/app/templates/base.html
similarity index 100%
rename from API/API-TRM/TRM/Back/app/templates/base.html
rename to TRM/back/app/templates/base.html
diff --git a/API/API-TRM/TRM/Back/app/templates/index.html b/TRM/back/app/templates/index.html
similarity index 100%
rename from API/API-TRM/TRM/Back/app/templates/index.html
rename to TRM/back/app/templates/index.html
diff --git a/API/API-TRM/TRM/Back/config.py b/TRM/back/config.py
similarity index 100%
rename from API/API-TRM/TRM/Back/config.py
rename to TRM/back/config.py
diff --git a/API/API-TRM/TRM/Back/requirements.txt b/TRM/back/requirements.txt
similarity index 100%
rename from API/API-TRM/TRM/Back/requirements.txt
rename to TRM/back/requirements.txt
diff --git a/API/API-TRM/TRM/Back/tests/__init__.py b/TRM/back/tests/__init__.py
similarity index 100%
rename from API/API-TRM/TRM/Back/tests/__init__.py
rename to TRM/back/tests/__init__.py
diff --git a/API/API-TRM/TRM/Back/tests/__pycache__/__init__.cpython-312.pyc b/TRM/back/tests/__pycache__/__init__.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/TRM/Back/tests/__pycache__/__init__.cpython-312.pyc
rename to TRM/back/tests/__pycache__/__init__.cpython-312.pyc
Binary files differ
diff --git a/TRM/back/tests/__pycache__/test_app.cpython-312-pytest-7.4.4.pyc b/TRM/back/tests/__pycache__/test_app.cpython-312-pytest-7.4.4.pyc
new file mode 100644
index 0000000..9a2b7de
--- /dev/null
+++ b/TRM/back/tests/__pycache__/test_app.cpython-312-pytest-7.4.4.pyc
Binary files differ
diff --git a/API/API-TRM/TRM/Back/tests/test_app.py b/TRM/back/tests/test_app.py
similarity index 60%
rename from API/API-TRM/TRM/Back/tests/test_app.py
rename to TRM/back/tests/test_app.py
index 5643282..3ed6bf9 100644
--- a/API/API-TRM/TRM/Back/tests/test_app.py
+++ b/TRM/back/tests/test_app.py
@@ -3,7 +3,7 @@
def test_get_postlist():
print()
- urlx=url+'spostlist'
+ urlx=url+'apostlist'
payload = {
'userid': 3
}
@@ -15,7 +15,7 @@
def test_get_post():
print()
- urlx=url+'sgetpost'
+ urlx=url+'agetpost'
payload = {
'userid': 3,
'postid': 21
@@ -24,4 +24,18 @@
resp = requests.get(urlx, json=payload, headers=headers)
# print(resp.status_code)
+ print(resp.json())
+
+def test_review_post():
+ print()
+ urlx=url+'areview'
+ payload = {
+ 'userid': 3,
+ 'postid': 21,
+ 'status': 'rejected'
+ }
+ headers = {'Content-Type': 'application/json'}
+
+ resp = requests.get(urlx, json=payload, headers=headers)
+ # print(resp.status_code)
print(resp.json())
\ No newline at end of file
diff --git a/API/API-TRM/TRM/Front/trm-front/.gitignore b/TRM/front/.gitignore
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/.gitignore
rename to TRM/front/.gitignore
diff --git a/API/API-TRM/TRM/Front/trm-front/README.md b/TRM/front/README.md
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/README.md
rename to TRM/front/README.md
diff --git a/API/API-TRM/TRM/Front/trm-front/package.json b/TRM/front/package.json
similarity index 89%
rename from API/API-TRM/TRM/Front/trm-front/package.json
rename to TRM/front/package.json
index dbe27a6..142eb20 100644
--- a/API/API-TRM/TRM/Front/trm-front/package.json
+++ b/TRM/front/package.json
@@ -1,5 +1,5 @@
{
- "name": "trm-front",
+ "name": "front",
"version": "0.1.0",
"private": true,
"dependencies": {
@@ -9,7 +9,8 @@
"@testing-library/user-event": "^13.5.0",
"react": "^19.1.0",
"react-dom": "^19.1.0",
- "react-scripts": "5.0.1",
+ "react-router-dom": "^6.14.1",
+ "react-scripts": "^5.0.1",
"web-vitals": "^2.1.4"
},
"scripts": {
diff --git a/API/API-TRM/TRM/Front/trm-front/public/favicon.ico b/TRM/front/public/favicon.ico
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/public/favicon.ico
rename to TRM/front/public/favicon.ico
Binary files differ
diff --git a/API/API-TRM/TRM/Front/trm-front/public/index.html b/TRM/front/public/index.html
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/public/index.html
rename to TRM/front/public/index.html
diff --git a/API/API-TRM/TRM/Front/trm-front/public/logo192.png b/TRM/front/public/logo192.png
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/public/logo192.png
rename to TRM/front/public/logo192.png
Binary files differ
diff --git a/API/API-TRM/TRM/Front/trm-front/public/logo512.png b/TRM/front/public/logo512.png
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/public/logo512.png
rename to TRM/front/public/logo512.png
Binary files differ
diff --git a/API/API-TRM/TRM/Front/trm-front/public/manifest.json b/TRM/front/public/manifest.json
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/public/manifest.json
rename to TRM/front/public/manifest.json
diff --git a/API/API-TRM/TRM/Front/trm-front/public/robots.txt b/TRM/front/public/robots.txt
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/public/robots.txt
rename to TRM/front/public/robots.txt
diff --git a/TRM/front/src/Admin.css b/TRM/front/src/Admin.css
new file mode 100644
index 0000000..1697483
--- /dev/null
+++ b/TRM/front/src/Admin.css
@@ -0,0 +1,65 @@
+.admin-container {
+ padding: 24px;
+ background-color: #fff;
+ font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
+}
+
+.admin-title {
+ font-size: 24px;
+ color: #e61515;
+ margin-bottom: 16px;
+}
+
+.admin-table {
+ width: 100%;
+ border-collapse: collapse;
+}
+
+.admin-table th,
+.admin-table td {
+ border: 1px solid #f0f0f0;
+ padding: 12px 16px;
+ text-align: left;
+}
+
+.admin-table th {
+ background-color: #fafafa;
+ color: #333;
+ font-weight: 500;
+}
+
+.status {
+ font-weight: 500;
+ text-transform: capitalize;
+}
+
+.status.pending {
+ color: #f29900;
+}
+
+.status.approved {
+ color: #28a745;
+}
+
+.status.banned {
+ color: #d73a49;
+}
+
+.btn {
+ padding: 6px 12px;
+ margin-right: 8px;
+ border: none;
+ border-radius: 4px;
+ cursor: pointer;
+ font-size: 14px;
+}
+
+.btn-approve {
+ background-color: #e61515;
+ color: #fff;
+}
+
+.btn-ban {
+ background-color: #f5f5f5;
+ color: #333;
+}
\ No newline at end of file
diff --git a/TRM/front/src/Admin.js b/TRM/front/src/Admin.js
new file mode 100644
index 0000000..1547706
--- /dev/null
+++ b/TRM/front/src/Admin.js
@@ -0,0 +1,75 @@
+import React, { useState, useEffect } from 'react';
+import './Admin.css';
+
+function AdminPage() {
+ const [posts, setPosts] = useState([]);
+
+ useEffect(() => {
+ // TODO: 替换成你后端真正的接口
+ fetch('/apostlist')
+ .then(res => res.json())
+ .then(data => setPosts(data))
+ .catch(console.error);
+ }, []);
+
+ const handleAction = (id, action) => {
+ // action: 'approve' | 'ban' | ...
+ fetch(`/api/posts/${id}/${action}`, { method: 'POST' })
+ .then(res => {
+ if (res.ok) {
+ // 简单地把该条移除或根据返回值更新状态
+ setPosts(ps => ps.filter(p => p.id !== id));
+ }
+ })
+ .catch(console.error);
+ };
+
+ return (
+ <div className="admin-container">
+ <h1 className="admin-title">小红书 · 管理员审核</h1>
+ <table className="admin-table">
+ <thead>
+ <tr>
+ <th>标题</th>
+ <th>发布时间</th>
+ <th>内容摘要</th>
+ <th>状态</th>
+ <th>操作</th>
+ </tr>
+ </thead>
+ <tbody>
+ {posts.map(p => {
+ const brief =
+ p.content.length > 80
+ ? p.content.slice(0, 80) + '...'
+ : p.content;
+ return (
+ <tr key={p.id}>
+ <td>{p.title}</td>
+ <td>{new Date(p.createdAt).toLocaleString()}</td>
+ <td>{brief}</td>
+ <td className={`status ${p.status}`}>{p.status}</td>
+ <td>
+ <button
+ className="btn btn-approve"
+ onClick={() => handleAction(p.id, 'approve')}
+ >
+ 审核
+ </button>
+ <button
+ className="btn btn-ban"
+ onClick={() => handleAction(p.id, 'ban')}
+ >
+ 封禁
+ </button>
+ </td>
+ </tr>
+ );
+ })}
+ </tbody>
+ </table>
+ </div>
+ );
+}
+
+export default AdminPage;
\ No newline at end of file
diff --git a/API/API-TRM/TRM/Front/trm-front/src/App.css b/TRM/front/src/App.css
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/src/App.css
rename to TRM/front/src/App.css
diff --git a/TRM/front/src/App.js b/TRM/front/src/App.js
new file mode 100644
index 0000000..581dfe9
--- /dev/null
+++ b/TRM/front/src/App.js
@@ -0,0 +1,28 @@
+import React from 'react';
+import {
+ Routes,
+ Route,
+ Navigate,
+} from 'react-router-dom';
+import AdminPage from './Admin';
+import UserManagement from './UserManagement';
+import LogsDashboard from './LogsDashboard';
+import SuperAdmin from './SuperAdmin';
+
+export default function App() {
+ return (
+ <Routes>
+ <Route path="/" element={<Navigate to="admin" replace />} />
+
+ {/* 普通管理员,无 header */}
+ <Route path="admin" element={<AdminPage />} />
+
+ {/* 超级管理员,只用 SuperAdminLayout */}
+ <Route path="superadmin" element={<SuperAdmin />}>
+ <Route index element={<Navigate to="users" replace />} />
+ <Route path="users" element={<UserManagement />} />
+ <Route path="dashboard" element={<LogsDashboard />} />
+ </Route>
+ </Routes>
+ );
+}
\ No newline at end of file
diff --git a/API/API-TRM/TRM/Front/trm-front/src/App.test.js b/TRM/front/src/App.test.js
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/src/App.test.js
rename to TRM/front/src/App.test.js
diff --git a/TRM/front/src/LogsDashboard.js b/TRM/front/src/LogsDashboard.js
new file mode 100644
index 0000000..c2e6239
--- /dev/null
+++ b/TRM/front/src/LogsDashboard.js
@@ -0,0 +1,45 @@
+import React, { useEffect, useState } from 'react';
+import './Admin.css';
+
+function LogsDashboard() {
+ const [logs, setLogs] = useState([]);
+ const [stats, setStats] = useState({});
+
+ useEffect(() => {
+ fetch('/api/logs')
+ .then(res => res.json())
+ .then(setLogs)
+ .catch(console.error);
+ fetch('/api/stats')
+ .then(res => res.json())
+ .then(setStats)
+ .catch(console.error);
+ }, []);
+
+ return (
+ <div className="admin-container">
+ <h2>运行日志 & 性能 Dashboard</h2>
+ <section className="dashboard-stats">
+ <pre>{JSON.stringify(stats, null, 2)}</pre>
+ </section>
+ <section className="dashboard-logs">
+ <table className="admin-table">
+ <thead>
+ <tr><th>时间</th><th>级别</th><th>消息</th></tr>
+ </thead>
+ <tbody>
+ {logs.map((log, i) => (
+ <tr key={i}>
+ <td>{new Date(log.time).toLocaleString()}</td>
+ <td>{log.level}</td>
+ <td>{log.message}</td>
+ </tr>
+ ))}
+ </tbody>
+ </table>
+ </section>
+ </div>
+ );
+}
+
+export default LogsDashboard;
diff --git a/TRM/front/src/SuperAdmin.css b/TRM/front/src/SuperAdmin.css
new file mode 100644
index 0000000..2295f8b
--- /dev/null
+++ b/TRM/front/src/SuperAdmin.css
@@ -0,0 +1,30 @@
+.super-admin-container {
+ display: flex;
+ height: 100vh;
+}
+
+.super-admin-sidebar {
+ width: 200px;
+ padding: 20px;
+ background: #f5f5f5;
+}
+
+.super-admin-sidebar ul {
+ list-style: none;
+ padding: 0;
+}
+
+.super-admin-sidebar li {
+ margin-bottom: 10px;
+}
+
+.super-admin-sidebar .active {
+ font-weight: bold;
+ color: #1890ff;
+}
+
+.super-admin-content {
+ flex: 1;
+ padding: 20px;
+ background: #fff;
+}
\ No newline at end of file
diff --git a/TRM/front/src/SuperAdmin.js b/TRM/front/src/SuperAdmin.js
new file mode 100644
index 0000000..0ddb9db
--- /dev/null
+++ b/TRM/front/src/SuperAdmin.js
@@ -0,0 +1,38 @@
+import React from 'react';
+import { NavLink, Outlet } from 'react-router-dom';
+import './SuperAdmin.css'; // 可选:自定义样式
+
+export default function SuperAdmin() {
+ return (
+ <div className="super-admin-container">
+ <aside className="super-admin-sidebar">
+ <h2>超级管理员</h2>
+ <nav>
+ <ul>
+ <li>
+ <NavLink
+ to="users"
+ end
+ className={({ isActive }) => isActive ? 'active' : ''}
+ >
+ 用户管理
+ </NavLink>
+ </li>
+ <li>
+ <NavLink
+ to="dashboard"
+ className={({ isActive }) => isActive ? 'active' : ''}
+ >
+ 平台运行监控
+ </NavLink>
+ </li>
+ </ul>
+ </nav>
+ </aside>
+
+ <main className="super-admin-content">
+ <Outlet />
+ </main>
+ </div>
+ );
+}
\ No newline at end of file
diff --git a/TRM/front/src/UserManagement.js b/TRM/front/src/UserManagement.js
new file mode 100644
index 0000000..ec7cbc2
--- /dev/null
+++ b/TRM/front/src/UserManagement.js
@@ -0,0 +1,44 @@
+import React, { useState, useEffect } from 'react';
+import './Admin.css';
+
+function UserManagement() {
+ const [users, setUsers] = useState([]);
+
+ useEffect(() => {
+ fetch('/api/users')
+ .then(res => res.json())
+ .then(data => setUsers(data))
+ .catch(console.error);
+ }, []);
+
+ const handleUserAction = (id, action) => {
+ fetch(`/api/users/${id}/${action}`, { method: 'POST' })
+ .then(res => res.ok && setUsers(us => us.filter(u => u.id !== id)))
+ .catch(console.error);
+ };
+
+ return (
+ <div className="admin-container">
+ <h2>用户管理</h2>
+ <table className="admin-table">
+ <thead>
+ <tr><th>用户名</th><th>角色</th><th>操作</th></tr>
+ </thead>
+ <tbody>
+ {users.map(u => (
+ <tr key={u.id}>
+ <td>{u.username}</td>
+ <td>{u.role}</td>
+ <td>
+ <button onClick={() => handleUserAction(u.id, 'ban')}>封禁</button>
+ <button onClick={() => handleUserAction(u.id, 'promote')}>提升权限</button>
+ </td>
+ </tr>
+ ))}
+ </tbody>
+ </table>
+ </div>
+ );
+}
+
+export default UserManagement;
diff --git a/API/API-TRM/TRM/Front/trm-front/src/index.css b/TRM/front/src/index.css
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/src/index.css
rename to TRM/front/src/index.css
diff --git a/TRM/front/src/index.js b/TRM/front/src/index.js
new file mode 100644
index 0000000..9c5a71b
--- /dev/null
+++ b/TRM/front/src/index.js
@@ -0,0 +1,14 @@
+import React from 'react';
+import ReactDOM from 'react-dom/client';
+import { BrowserRouter } from 'react-router-dom';
+import './index.css';
+import App from './App';
+
+const root = ReactDOM.createRoot(document.getElementById('root'));
+root.render(
+ <React.StrictMode>
+ <BrowserRouter>
+ <App />
+ </BrowserRouter>
+ </React.StrictMode>
+);
\ No newline at end of file
diff --git a/API/API-TRM/TRM/Front/trm-front/src/logo.svg b/TRM/front/src/logo.svg
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/src/logo.svg
rename to TRM/front/src/logo.svg
diff --git a/API/API-TRM/TRM/Front/trm-front/src/reportWebVitals.js b/TRM/front/src/reportWebVitals.js
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/src/reportWebVitals.js
rename to TRM/front/src/reportWebVitals.js
diff --git a/API/API-TRM/TRM/Front/trm-front/src/setupTests.js b/TRM/front/src/setupTests.js
similarity index 100%
rename from API/API-TRM/TRM/Front/trm-front/src/setupTests.js
rename to TRM/front/src/setupTests.js
diff --git a/API/API-TRM/WZY/xhs_front/README.md b/WZY/xhs_front/README.md
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/README.md
rename to WZY/xhs_front/README.md
diff --git a/API/API-TRM/WZY/xhs_front/index.html b/WZY/xhs_front/index.html
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/index.html
rename to WZY/xhs_front/index.html
diff --git a/API/API-TRM/WZY/xhs_front/package.json b/WZY/xhs_front/package.json
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/package.json
rename to WZY/xhs_front/package.json
diff --git a/API/API-TRM/WZY/xhs_front/public/vite.svg b/WZY/xhs_front/public/vite.svg
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/public/vite.svg
rename to WZY/xhs_front/public/vite.svg
diff --git a/API/API-TRM/WZY/xhs_front/src/App.css b/WZY/xhs_front/src/App.css
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/App.css
rename to WZY/xhs_front/src/App.css
diff --git a/API/API-TRM/WZY/xhs_front/src/App.jsx b/WZY/xhs_front/src/App.jsx
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/App.jsx
rename to WZY/xhs_front/src/App.jsx
diff --git a/API/API-TRM/WZY/xhs_front/src/api/posts.js b/WZY/xhs_front/src/api/posts.js
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/api/posts.js
rename to WZY/xhs_front/src/api/posts.js
diff --git a/API/API-TRM/WZY/xhs_front/src/components/CreatePost.jsx b/WZY/xhs_front/src/components/CreatePost.jsx
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/components/CreatePost.jsx
rename to WZY/xhs_front/src/components/CreatePost.jsx
diff --git a/API/API-TRM/WZY/xhs_front/src/components/Header.jsx b/WZY/xhs_front/src/components/Header.jsx
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/components/Header.jsx
rename to WZY/xhs_front/src/components/Header.jsx
diff --git a/API/API-TRM/WZY/xhs_front/src/components/HomeFeed.jsx b/WZY/xhs_front/src/components/HomeFeed.jsx
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/components/HomeFeed.jsx
rename to WZY/xhs_front/src/components/HomeFeed.jsx
diff --git a/API/API-TRM/WZY/xhs_front/src/components/PlaceholderPage.jsx b/WZY/xhs_front/src/components/PlaceholderPage.jsx
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/components/PlaceholderPage.jsx
rename to WZY/xhs_front/src/components/PlaceholderPage.jsx
diff --git a/API/API-TRM/WZY/xhs_front/src/components/Sidebar.jsx b/WZY/xhs_front/src/components/Sidebar.jsx
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/components/Sidebar.jsx
rename to WZY/xhs_front/src/components/Sidebar.jsx
diff --git a/API/API-TRM/WZY/xhs_front/src/components/UploadPage.jsx b/WZY/xhs_front/src/components/UploadPage.jsx
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/components/UploadPage.jsx
rename to WZY/xhs_front/src/components/UploadPage.jsx
diff --git a/API/API-TRM/WZY/xhs_front/src/index.css b/WZY/xhs_front/src/index.css
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/index.css
rename to WZY/xhs_front/src/index.css
diff --git a/API/API-TRM/WZY/xhs_front/src/main.jsx b/WZY/xhs_front/src/main.jsx
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/main.jsx
rename to WZY/xhs_front/src/main.jsx
diff --git a/API/API-TRM/WZY/xhs_front/src/router/index.jsx b/WZY/xhs_front/src/router/index.jsx
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/router/index.jsx
rename to WZY/xhs_front/src/router/index.jsx
diff --git a/API/API-TRM/WZY/xhs_front/src/style/CreatePost.css b/WZY/xhs_front/src/style/CreatePost.css
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/style/CreatePost.css
rename to WZY/xhs_front/src/style/CreatePost.css
diff --git a/API/API-TRM/WZY/xhs_front/src/style/HomeFeed.css b/WZY/xhs_front/src/style/HomeFeed.css
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/src/style/HomeFeed.css
rename to WZY/xhs_front/src/style/HomeFeed.css
diff --git a/API/API-TRM/WZY/xhs_front/vite.config.js b/WZY/xhs_front/vite.config.js
similarity index 100%
rename from API/API-TRM/WZY/xhs_front/vite.config.js
rename to WZY/xhs_front/vite.config.js
diff --git a/API/API-TRM/WZY/xhs_server/__pycache__/app.cpython-312.pyc b/WZY/xhs_server/__pycache__/app.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/__pycache__/app.cpython-312.pyc
rename to WZY/xhs_server/__pycache__/app.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/__pycache__/config.cpython-312.pyc b/WZY/xhs_server/__pycache__/config.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/__pycache__/config.cpython-312.pyc
rename to WZY/xhs_server/__pycache__/config.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/__pycache__/extensions.cpython-312.pyc b/WZY/xhs_server/__pycache__/extensions.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/__pycache__/extensions.cpython-312.pyc
rename to WZY/xhs_server/__pycache__/extensions.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/all_tables.sql b/WZY/xhs_server/all_tables.sql
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/all_tables.sql
rename to WZY/xhs_server/all_tables.sql
diff --git a/API/API-TRM/WZY/xhs_server/app.py b/WZY/xhs_server/app.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/app.py
rename to WZY/xhs_server/app.py
diff --git a/API/API-TRM/WZY/xhs_server/config.py b/WZY/xhs_server/config.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/config.py
rename to WZY/xhs_server/config.py
diff --git a/API/API-TRM/WZY/xhs_server/extensions.py b/WZY/xhs_server/extensions.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/extensions.py
rename to WZY/xhs_server/extensions.py
diff --git a/API/API-TRM/WZY/xhs_server/manage.py b/WZY/xhs_server/manage.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/manage.py
rename to WZY/xhs_server/manage.py
diff --git a/API/API-TRM/WZY/xhs_server/models/__init__.py b/WZY/xhs_server/models/__init__.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/__init__.py
rename to WZY/xhs_server/models/__init__.py
diff --git a/API/API-TRM/WZY/xhs_server/models/__pycache__/__init__.cpython-312.pyc b/WZY/xhs_server/models/__pycache__/__init__.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/__pycache__/__init__.cpython-312.pyc
rename to WZY/xhs_server/models/__pycache__/__init__.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/models/__pycache__/behavior.cpython-312.pyc b/WZY/xhs_server/models/__pycache__/behavior.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/__pycache__/behavior.cpython-312.pyc
rename to WZY/xhs_server/models/__pycache__/behavior.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/models/__pycache__/comment.cpython-312.pyc b/WZY/xhs_server/models/__pycache__/comment.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/__pycache__/comment.cpython-312.pyc
rename to WZY/xhs_server/models/__pycache__/comment.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/models/__pycache__/post.cpython-312.pyc b/WZY/xhs_server/models/__pycache__/post.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/__pycache__/post.cpython-312.pyc
rename to WZY/xhs_server/models/__pycache__/post.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/models/__pycache__/tag.cpython-312.pyc b/WZY/xhs_server/models/__pycache__/tag.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/__pycache__/tag.cpython-312.pyc
rename to WZY/xhs_server/models/__pycache__/tag.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/models/__pycache__/topic.cpython-312.pyc b/WZY/xhs_server/models/__pycache__/topic.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/__pycache__/topic.cpython-312.pyc
rename to WZY/xhs_server/models/__pycache__/topic.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/models/__pycache__/user.cpython-312.pyc b/WZY/xhs_server/models/__pycache__/user.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/__pycache__/user.cpython-312.pyc
rename to WZY/xhs_server/models/__pycache__/user.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/models/behavior.py b/WZY/xhs_server/models/behavior.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/behavior.py
rename to WZY/xhs_server/models/behavior.py
diff --git a/API/API-TRM/WZY/xhs_server/models/comment.py b/WZY/xhs_server/models/comment.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/comment.py
rename to WZY/xhs_server/models/comment.py
diff --git a/API/API-TRM/WZY/xhs_server/models/post.py b/WZY/xhs_server/models/post.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/post.py
rename to WZY/xhs_server/models/post.py
diff --git a/API/API-TRM/WZY/xhs_server/models/tag.py b/WZY/xhs_server/models/tag.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/tag.py
rename to WZY/xhs_server/models/tag.py
diff --git a/API/API-TRM/WZY/xhs_server/models/topic.py b/WZY/xhs_server/models/topic.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/topic.py
rename to WZY/xhs_server/models/topic.py
diff --git a/API/API-TRM/WZY/xhs_server/models/user.py b/WZY/xhs_server/models/user.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/models/user.py
rename to WZY/xhs_server/models/user.py
diff --git a/API/API-TRM/WZY/xhs_server/readme.md b/WZY/xhs_server/readme.md
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/readme.md
rename to WZY/xhs_server/readme.md
diff --git a/API/API-TRM/WZY/xhs_server/requirements.txt b/WZY/xhs_server/requirements.txt
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/requirements.txt
rename to WZY/xhs_server/requirements.txt
diff --git a/API/API-TRM/WZY/xhs_server/routes/__init__.py b/WZY/xhs_server/routes/__init__.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/routes/__init__.py
rename to WZY/xhs_server/routes/__init__.py
diff --git a/API/API-TRM/WZY/xhs_server/routes/__pycache__/__init__.cpython-312.pyc b/WZY/xhs_server/routes/__pycache__/__init__.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/routes/__pycache__/__init__.cpython-312.pyc
rename to WZY/xhs_server/routes/__pycache__/__init__.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/routes/__pycache__/comments.cpython-312.pyc b/WZY/xhs_server/routes/__pycache__/comments.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/routes/__pycache__/comments.cpython-312.pyc
rename to WZY/xhs_server/routes/__pycache__/comments.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/routes/__pycache__/posts.cpython-312.pyc b/WZY/xhs_server/routes/__pycache__/posts.cpython-312.pyc
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/routes/__pycache__/posts.cpython-312.pyc
rename to WZY/xhs_server/routes/__pycache__/posts.cpython-312.pyc
Binary files differ
diff --git a/API/API-TRM/WZY/xhs_server/routes/comments.py b/WZY/xhs_server/routes/comments.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/routes/comments.py
rename to WZY/xhs_server/routes/comments.py
diff --git a/API/API-TRM/WZY/xhs_server/routes/posts.py b/WZY/xhs_server/routes/posts.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/routes/posts.py
rename to WZY/xhs_server/routes/posts.py
diff --git a/API/API-TRM/WZY/xhs_server/utils/auth.py b/WZY/xhs_server/utils/auth.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/utils/auth.py
rename to WZY/xhs_server/utils/auth.py
diff --git a/API/API-TRM/WZY/xhs_server/utils/serializers.py b/WZY/xhs_server/utils/serializers.py
similarity index 100%
rename from API/API-TRM/WZY/xhs_server/utils/serializers.py
rename to WZY/xhs_server/utils/serializers.py
diff --git a/xiaohongshu-upload-platform/README.md b/xiaohongshu-upload-platform/README.md
deleted file mode 100644
index 6f35930..0000000
--- a/xiaohongshu-upload-platform/README.md
+++ /dev/null
@@ -1,185 +0,0 @@
-# 小红书内容创作平台
-
-这是一个基于 React + Vite 构建的小红书内容创作平台界面,完全复制了小红书官方创作服务平台的设计和功能。
-
-## 功能特性 ✨
-
-### 🎨 界面设计
-- **完全还原小红书官方设计**:精确复制了小红书创作服务平台的视觉风格
-- **响应式布局**:支持桌面端和移动端适配
-- **现代化UI**:使用 Lucide React 图标库,提供清晰美观的界面
-
-### 📤 上传功能
-- **双模式上传**:支持图片上传和视频上传两种模式
-- **拖拽上传**:支持文件拖拽到上传区域
-- **点击上传**:点击按钮选择文件上传
-- **文件验证**:
- - 图片:支持 JPEG、JPG、PNG、WebP 格式,最大 32MB
- - 视频:支持 MP4、MOV、AVI 格式,最大 2GB
-- **实时进度显示**:带有动画效果的上传进度条
-
-### 🖼️ 文件管理
-- **文件预览**:上传后实时显示文件缩略图
-- **文件信息**:显示文件名、大小等详细信息
-- **批量管理**:支持单个删除和批量清除
-- **文件计数**:实时显示已上传文件数量
-
-### 🎯 交互体验
-- **拖拽反馈**:拖拽时提供视觉反馈效果
-- **加载状态**:上传过程中的加载动画
-- **操作提示**:完成上传后的成功提示
-- **悬停效果**:按钮和文件项的悬停交互
-
-### 🗂️ 导航系统
-- **侧边栏导航**:完整的功能菜单
-- **可展开子菜单**:数据看板等功能的子选项
-- **活跃状态**:当前选中页面的高亮显示
-- **固定布局**:头部和侧边栏固定定位
-
-## 技术栈 🛠️
-
-- **前端框架**:React 19.1.0
-- **构建工具**:Vite 6.0.5
-- **图标库**:Lucide React 0.468.0
-- **样式**:纯 CSS(无预处理器)
-- **开发语言**:JavaScript + JSX
-
-## 安装运行 🚀
-
-1. **安装依赖**
- ```bash
- npm install
- ```
-
-2. **启动开发服务器**
- ```bash
- npm run dev
- ```
-
-3. **打开浏览器**
- ```
- http://localhost:5173
- ```
-
-4. **构建生产版本**
- ```bash
- npm run build
- ```
-
-## 项目结构 📁
-
-```
-发布页面/
-├── public/ # 静态资源
-│ └── vite.svg # Vite 图标
-├── src/
-│ ├── App.jsx # 主应用组件
-│ ├── App.css # 主样式文件
-│ ├── index.css # 全局样式
-│ └── main.jsx # 应用入口
-├── index.html # HTML 入口文件
-├── package.json # 项目配置
-├── vite.config.js # Vite 配置
-└── README.md # 项目说明
-```
-
-## 核心功能实现 💡
-
-### 文件上传处理
-```javascript
-const handleFileUpload = () => {
- const input = document.createElement('input')
- input.type = 'file'
- input.accept = activeTab === 'video' ? 'video/*' : 'image/*'
- input.multiple = activeTab === 'image'
-
- input.onchange = (e) => {
- const files = Array.from(e.target.files)
- if (files.length > 0 && validateFiles(files)) {
- simulateUpload(files)
- }
- }
-
- input.click()
-}
-```
-
-### 拖拽上传实现
-```javascript
-const handleDrop = (e) => {
- e.preventDefault()
- e.stopPropagation()
- setIsDragOver(false)
-
- const files = Array.from(e.dataTransfer.files)
- if (files.length > 0 && validateFiles(files)) {
- simulateUpload(files)
- }
-}
-```
-
-### 文件验证机制
-```javascript
-const validateFiles = (files) => {
- const validImageTypes = ['image/jpeg', 'image/jpg', 'image/png', 'image/webp']
- const validVideoTypes = ['video/mp4', 'video/mov', 'video/avi']
-
- const validTypes = activeTab === 'video' ? validVideoTypes : validImageTypes
- const maxSize = activeTab === 'video' ? 2 * 1024 * 1024 * 1024 : 32 * 1024 * 1024
-
- return files.every(file =>
- validTypes.includes(file.type) && file.size <= maxSize
- )
-}
-```
-
-## 样式特色 🎨
-
-### 响应式设计
-- 桌面端:固定侧边栏布局
-- 移动端:隐藏侧边栏,堆叠布局
-- 自适应文件网格:根据屏幕大小调整列数
-
-### 动画效果
-- 拖拽时的放大效果
-- 进度条的流光动画
-- 文件项的悬停过渡
-- 页面切换的淡入效果
-
-### 色彩方案
-- 主色调:#ff4757(小红书红)
-- 背景色:#f5f7fa(浅灰蓝)
-- 文字色:#333(深灰)
-- 边框色:#e8eaed(浅灰)
-
-## 待扩展功能 🔮
-
-- **后端集成**:连接真实的文件上传 API
-- **用户认证**:登录注册功能
-- **内容编辑**:笔记内容编辑器
-- **数据统计**:真实的数据看板功能
-- **社交功能**:评论、点赞等互动功能
-
-## 开发说明 📝
-
-这个项目完全基于前端实现,所有的上传功能都是模拟的。文件预览使用了 `URL.createObjectURL()` 来生成本地预览链接。在实际部署时,需要:
-
-1. 集成后端文件上传 API
-2. 实现用户认证系统
-3. 添加数据持久化
-4. 优化性能和安全性
-
-## 浏览器兼容性 🌐
-
-- Chrome 90+
-- Firefox 88+
-- Safari 14+
-- Edge 90+
-
-## 许可证 📄
-
-MIT License
-
----
-
-**注意**:本项目仅用于学习和演示目的,请遵守相关法律法规和平台使用条款。
diff --git a/xiaohongshu-upload-platform/index.html b/xiaohongshu-upload-platform/index.html
deleted file mode 100644
index b919940..0000000
--- a/xiaohongshu-upload-platform/index.html
+++ /dev/null
@@ -1,13 +0,0 @@
-<!doctype html>
-<html lang="zh-CN">
- <head>
- <meta charset="UTF-8" />
- <link rel="icon" type="image/svg+xml" href="/vite.svg" />
- <meta name="viewport" content="width=device-width, initial-scale=1.0" />
- <title>小红书创作服务平台</title>
- </head>
- <body>
- <div id="root"></div>
- <script type="module" src="/src/main.jsx"></script>
- </body>
-</html>
diff --git a/xiaohongshu-upload-platform/package.json b/xiaohongshu-upload-platform/package.json
deleted file mode 100644
index 00a233f..0000000
--- a/xiaohongshu-upload-platform/package.json
+++ /dev/null
@@ -1,20 +0,0 @@
-{
- "name": "xiaohongshu-creator-platform",
- "private": true,
- "version": "0.0.0",
- "type": "module",
- "scripts": {
- "dev": "vite",
- "build": "vite build",
- "preview": "vite preview"
- },
- "dependencies": {
- "react": "^18.3.1",
- "react-dom": "^18.3.1",
- "lucide-react": "^0.468.0"
- },
- "devDependencies": {
- "@vitejs/plugin-react": "^4.3.4",
- "vite": "^6.0.5"
- }
-}
diff --git a/xiaohongshu-upload-platform/public/vite.svg b/xiaohongshu-upload-platform/public/vite.svg
deleted file mode 100644
index ee9fada..0000000
--- a/xiaohongshu-upload-platform/public/vite.svg
+++ /dev/null
@@ -1 +0,0 @@
-<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" aria-hidden="true" role="img" class="iconify iconify--logos" width="31.88" height="32" preserveAspectRatio="xMidYMid meet" viewBox="0 0 256 257"><defs><linearGradient id="IconifyId1813088fe1fbc01fb466" x1="-.828%" x2="57.636%" y1="7.652%" y2="78.411%"><stop offset="0%" stop-color="#41D1FF"></stop><stop offset="100%" stop-color="#BD34FE"></stop></linearGradient><linearGradient id="IconifyId1813088fe1fbc01fb467" x1="43.376%" x2="50.316%" y1="2.242%" y2="89.03%"><stop offset="0%" stop-color="#FFEA83"></stop><stop offset="8.333%" stop-color="#FFDD35"></stop><stop offset="100%" stop-color="#FFA800"></stop></linearGradient></defs><path fill="url(#IconifyId1813088fe1fbc01fb466)" d="M255.153 37.938L134.897 252.976c-2.483 4.44-8.862 4.466-11.382.048L.875 37.958c-2.746-4.814 1.371-10.646 6.827-9.67l120.385 21.517a6.537 6.537 0 0 0 2.322-.004l117.867-21.483c5.438-.991 9.574 4.796 6.877 9.62Z"></path><path fill="url(#IconifyId1813088fe1fbc01fb467)" d="M185.432.063L96.44 17.501a3.268 3.268 0 0 0-2.634 3.014l-5.474 92.456a3.268 3.268 0 0 0 3.997 3.378l24.777-5.718c2.318-.535 4.413 1.507 3.936 3.838l-7.361 36.047c-.495 2.426 1.782 4.5 4.151 3.78l15.304-4.649c2.372-.72 4.652 1.36 4.15 3.788l-11.698 56.621c-.732 3.542 3.979 5.473 5.943 2.437l1.313-2.028l72.516-144.72c1.215-2.423-.88-5.186-3.54-4.672l-25.505 4.922c-2.396.462-4.435-1.77-3.759-4.114l16.646-57.705c.677-2.35-1.37-4.583-3.769-4.113Z"></path></svg>
diff --git a/xiaohongshu-upload-platform/src/App.css b/xiaohongshu-upload-platform/src/App.css
deleted file mode 100644
index 00d10d6..0000000
--- a/xiaohongshu-upload-platform/src/App.css
+++ /dev/null
@@ -1,583 +0,0 @@
-.app {
- display: flex;
- min-height: 100vh;
- background-color: #f5f7fa;
-}
-
-/* Header */
-.header {
- position: fixed;
- top: 0;
- left: 0;
- right: 0;
- height: 60px;
- background: #fff;
- border-bottom: 1px solid #e8eaed;
- display: flex;
- align-items: center;
- padding: 0 20px;
- z-index: 1000;
- box-shadow: 0 1px 3px rgba(0, 0, 0, 0.1);
-}
-
-.header-left {
- display: flex;
- align-items: center;
- gap: 12px;
-}
-
-.logo {
- background: #ff4757;
- color: white;
- padding: 6px 12px;
- border-radius: 6px;
- font-size: 14px;
- font-weight: bold;
-}
-
-.header-title {
- font-size: 18px;
- font-weight: 500;
- color: #333;
-}
-
-.header-right {
- margin-left: auto;
- display: flex;
- align-items: center;
- gap: 12px;
-}
-
-.user-info {
- display: flex;
- align-items: center;
- gap: 8px;
- color: #666;
- font-size: 14px;
-}
-
-/* Sidebar */
-.sidebar {
- position: fixed;
- left: 0;
- top: 60px;
- width: 200px;
- height: calc(100vh - 60px);
- background: #fff;
- border-right: 1px solid #e8eaed;
- overflow-y: auto;
- z-index: 999;
-}
-
-.publish-btn {
- margin: 16px;
- background: #ff4757;
- color: white;
- padding: 10px 16px;
- border-radius: 6px;
- font-size: 14px;
- font-weight: 500;
- text-align: center;
- transition: background 0.2s;
-}
-
-.publish-btn:hover {
- background: #ff3742;
-}
-
-.nav-menu {
- padding: 0;
- list-style: none;
-}
-
-.nav-item {
- border-bottom: 1px solid #f0f0f0;
-}
-
-.nav-link {
- display: flex;
- align-items: center;
- padding: 12px 20px;
- color: #333;
- font-size: 14px;
- transition: all 0.2s;
- gap: 8px;
-}
-
-.nav-link:hover {
- background: #f8f9fa;
- color: #ff4757;
-}
-
-.nav-link.active {
- background: linear-gradient(135deg, #ff4757, #ff6b7a);
- color: white;
- font-weight: 500;
-}
-
-.nav-link.active .lucide {
- color: white;
-}
-
-.nav-submenu {
- padding-left: 20px;
- background: #fafafa;
-}
-
-.nav-submenu .nav-link {
- padding: 8px 20px;
- font-size: 13px;
- color: #666;
-}
-
-.nav-submenu .nav-link:hover {
- color: #ff4757;
-}
-
-/* Main Content */
-.main-content {
- margin-left: 200px;
- padding-top: 60px;
- flex: 1;
- min-height: 100vh;
-}
-
-.content-wrapper {
- padding: 20px;
- max-width: 1200px;
- margin: 0 auto;
-}
-
-/* Upload Area */
-.upload-tabs {
- display: flex;
- gap: 20px;
- margin-bottom: 30px;
- border-bottom: 1px solid #e8eaed;
-}
-
-.upload-tab {
- padding: 12px 0;
- font-size: 16px;
- color: #666;
- cursor: pointer;
- border-bottom: 2px solid transparent;
- transition: all 0.2s;
-}
-
-.upload-tab.active {
- color: #ff4757;
- border-bottom-color: #ff4757;
- font-weight: 500;
-}
-
-.upload-area {
- background: #fff;
- border-radius: 8px;
- padding: 80px 40px;
- text-align: center;
- border: 2px dashed #ddd;
- margin-bottom: 40px;
- transition: all 0.2s;
- min-height: 300px;
- display: flex;
- flex-direction: column;
- justify-content: center;
- align-items: center;
- position: relative;
-}
-
-.upload-area:hover {
- border-color: #ff4757;
- background: #fff8f8;
-}
-
-.upload-area.drag-over {
- border-color: #ff4757;
- background: #fff0f0;
- transform: scale(1.02);
-}
-
-.upload-icon {
- width: 100px;
- height: 100px;
- margin: 0 auto 30px;
- background: #f8f9fa;
- border-radius: 50%;
- display: flex;
- align-items: center;
- justify-content: center;
- font-size: 40px;
- color: #ccc;
- transition: all 0.3s ease;
-}
-
-.upload-area:hover .upload-icon {
- background: #ff475710;
- color: #ff4757;
- transform: scale(1.1);
-}
-
-.upload-area.drag-over .upload-icon {
- background: #ff475720;
- color: #ff4757;
- transform: scale(1.2);
-}
-
-.upload-title {
- font-size: 20px;
- color: #333;
- margin-bottom: 12px;
- font-weight: 500;
-}
-
-.upload-subtitle {
- font-size: 14px;
- color: #999;
- margin-bottom: 30px;
-}
-
-.upload-btn {
- background: #ff4757;
- color: white;
- padding: 14px 28px;
- border-radius: 6px;
- font-size: 16px;
- font-weight: 500;
- transition: background 0.2s;
- min-width: 120px;
-}
-
-.upload-btn:hover:not(:disabled) {
- background: #ff3742;
-}
-
-.upload-btn:disabled {
- background: #ccc;
- cursor: not-allowed;
-}
-
-.upload-btn.uploading {
- background: #ff4757;
- opacity: 0.8;
-}
-
-/* File Preview */
-.file-preview-area {
- background: #fff;
- border-radius: 8px;
- padding: 20px;
- margin-bottom: 40px;
- border: 1px solid #e8eaed;
-}
-
-/* Preview Header */
-.preview-header {
- display: flex;
- justify-content: space-between;
- align-items: center;
- margin-bottom: 16px;
-}
-
-.preview-title {
- font-size: 16px;
- color: #333;
- margin-bottom: 16px;
- font-weight: 500;
-}
-
-.clear-files-btn {
- background: #ff4757;
- color: white;
- padding: 6px 12px;
- border-radius: 4px;
- font-size: 12px;
- transition: background 0.2s;
-}
-
-.clear-files-btn:hover {
- background: #ff3742;
-}
-
-.file-grid {
- display: grid;
- grid-template-columns: repeat(auto-fill, minmax(120px, 1fr));
- gap: 16px;
-}
-
-.file-item {
- display: flex;
- flex-direction: column;
- align-items: center;
- padding: 12px;
- border: 1px solid #f0f0f0;
- border-radius: 6px;
- transition: all 0.2s ease;
- position: relative;
-}
-
-.file-item:hover {
- border-color: #ff4757;
- box-shadow: 0 2px 8px rgba(255, 71, 87, 0.1);
-}
-
-.file-item:hover .remove-file-btn {
- opacity: 1;
-}
-
-.remove-file-btn {
- position: absolute;
- top: 4px;
- right: 4px;
- background: rgba(255, 71, 87, 0.8);
- color: white;
- border-radius: 50%;
- width: 20px;
- height: 20px;
- display: flex;
- align-items: center;
- justify-content: center;
- font-size: 14px;
- font-weight: bold;
- opacity: 0;
- transition: all 0.2s;
-}
-
-.file-thumbnail {
- width: 80px;
- height: 80px;
- border-radius: 6px;
- overflow: hidden;
- margin-bottom: 8px;
- display: flex;
- align-items: center;
- justify-content: center;
- background: #f8f9fa;
-}
-
-.file-thumbnail img {
- width: 100%;
- height: 100%;
- object-fit: cover;
-}
-
-.video-thumbnail {
- color: #666;
-}
-
-.file-info {
- text-align: center;
- width: 100%;
-}
-
-.file-name {
- font-size: 12px;
- color: #333;
- margin-bottom: 4px;
- font-weight: 500;
-}
-
-.file-size {
- font-size: 11px;
- color: #999;
-}
-
-/* Upload Progress */
-.progress-container {
- margin-top: 20px;
- width: 100%;
- max-width: 400px;
-}
-
-.progress-bar {
- width: 100%;
- height: 8px;
- background-color: #f0f0f0;
- border-radius: 4px;
- overflow: hidden;
- margin-bottom: 8px;
-}
-
-.progress-fill {
- height: 100%;
- background: linear-gradient(90deg, #ff4757, #ff6b7a);
- border-radius: 4px;
- transition: width 0.3s ease;
- position: relative;
-}
-
-.progress-fill::after {
- content: '';
- position: absolute;
- top: 0;
- left: 0;
- right: 0;
- bottom: 0;
- background: linear-gradient(90deg, transparent, rgba(255, 255, 255, 0.3), transparent);
- animation: shimmer 1.5s infinite;
-}
-
-@keyframes shimmer {
- 0% { transform: translateX(-100%); }
- 100% { transform: translateX(100%); }
-}
-
-.progress-text {
- text-align: center;
- font-size: 12px;
- color: #666;
- font-weight: 500;
-}
-
-/* Upload Info */
-.upload-info {
- display: flex;
- gap: 60px;
- justify-content: center;
- margin-top: 40px;
- padding: 20px;
- opacity: 1;
- transition: opacity 0.3s ease;
-}
-
-.upload-info.fade-in {
- animation: fadeIn 0.3s ease-in-out;
-}
-
-@keyframes fadeIn {
- from {
- opacity: 0;
- transform: translateY(10px);
- }
- to {
- opacity: 1;
- transform: translateY(0);
- }
-}
-
-.info-item {
- text-align: center;
- flex: 1;
- max-width: 300px;
-}
-
-.info-title {
- font-size: 16px;
- color: #333;
- margin-bottom: 12px;
- font-weight: 500;
-}
-
-.info-desc {
- font-size: 13px;
- color: #666;
- line-height: 1.6;
-}
-
-/* Page Content Styles */
-.page-content {
- padding: 40px;
- background: white;
- border-radius: 12px;
- box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
- margin: 20px 0;
- min-height: 500px;
-}
-
-.page-header {
- margin-bottom: 40px;
- padding-bottom: 20px;
- border-bottom: 1px solid #e8eaed;
-}
-
-.page-title {
- font-size: 24px;
- font-weight: 600;
- color: #333;
- margin: 0;
-}
-
-.page-body {
- display: flex;
- align-items: center;
- justify-content: center;
- min-height: 400px;
-}
-
-.placeholder-content {
- text-align: center;
- max-width: 400px;
-}
-
-.placeholder-icon {
- color: #ff4757;
- margin-bottom: 20px;
- display: flex;
- justify-content: center;
-}
-
-.placeholder-title {
- font-size: 20px;
- font-weight: 500;
- color: #333;
- margin: 0 0 15px 0;
-}
-
-.placeholder-desc {
- font-size: 14px;
- color: #666;
- line-height: 1.6;
- margin: 0;
-}
-
-/* Responsive */
-@media (max-width: 768px) {
- .sidebar {
- transform: translateX(-100%);
- transition: transform 0.3s;
- }
-
- .main-content {
- margin-left: 0;
- }
-
- .header-title {
- display: none;
- }
-
- .upload-area {
- padding: 60px 20px;
- margin: 0 10px 30px;
- }
-
- .upload-info {
- flex-direction: column;
- gap: 30px;
- padding: 10px;
- }
-
- .content-wrapper {
- padding: 15px;
- }
-
- .upload-tabs {
- gap: 15px;
- }
-
- .page-content {
- padding: 20px;
- margin: 10px;
- }
-
- .page-title {
- font-size: 20px;
- }
-
- .placeholder-title {
- font-size: 18px;
- }
-
- .placeholder-desc {
- font-size: 13px;
- }
-}
diff --git a/xiaohongshu-upload-platform/src/App.jsx b/xiaohongshu-upload-platform/src/App.jsx
deleted file mode 100644
index 8388b7b..0000000
--- a/xiaohongshu-upload-platform/src/App.jsx
+++ /dev/null
@@ -1,410 +0,0 @@
-import React, { useState } from 'react'
-import {
- Home,
- Settings,
- BarChart3,
- PieChart,
- TrendingUp,
- Activity,
- BookOpen,
- Users,
- Upload,
- Image,
- Video,
- ChevronDown,
- User
-} from 'lucide-react'
-import './App.css'
-
-function App() {
- const [activeTab, setActiveTab] = useState('image')
- const [expandedMenu, setExpandedMenu] = useState('dashboard')
- const [activePage, setActivePage] = useState('dashboard') // 新增:当前激活的页面
- const [isDragOver, setIsDragOver] = useState(false)
- const [isUploading, setIsUploading] = useState(false)
- const [uploadedFiles, setUploadedFiles] = useState([])
- const [uploadProgress, setUploadProgress] = useState(0)
-
- const validateFiles = (files) => {
- const validImageTypes = ['image/jpeg', 'image/jpg', 'image/png', 'image/webp']
- const validVideoTypes = ['video/mp4', 'video/mov', 'video/avi']
-
- const validTypes = activeTab === 'video' ? validVideoTypes : validImageTypes
- const maxSize = activeTab === 'video' ? 2 * 1024 * 1024 * 1024 : 32 * 1024 * 1024 // 2GB for video, 32MB for images
-
- const invalidFiles = files.filter(file => {
- return !validTypes.includes(file.type) || file.size > maxSize
- })
-
- if (invalidFiles.length > 0) {
- alert(`发现 ${invalidFiles.length} 个无效文件,请检查文件格式和大小`)
- return false
- }
-
- return true
- }
-
- const simulateUpload = (files) => {
- setIsUploading(true)
- setUploadProgress(0)
- setUploadedFiles(files)
-
- // 模拟上传进度
- const interval = setInterval(() => {
- setUploadProgress(prev => {
- if (prev >= 100) {
- clearInterval(interval)
- setIsUploading(false)
- alert(`成功上传了 ${files.length} 个文件`)
- return 100
- }
- return prev + 10
- })
- }, 200)
- }
-
- const handleFileUpload = () => {
- if (isUploading) return
-
- const input = document.createElement('input')
- input.type = 'file'
- input.accept = activeTab === 'video' ? 'video/*' : 'image/*'
- input.multiple = activeTab === 'image'
- input.onchange = (e) => {
- const files = Array.from(e.target.files)
- if (files.length > 0 && validateFiles(files)) {
- simulateUpload(files)
- }
- }
- input.click()
- }
-
- const handleDragOver = (e) => {
- e.preventDefault()
- e.stopPropagation()
- setIsDragOver(true)
- }
-
- const handleDragLeave = (e) => {
- e.preventDefault()
- e.stopPropagation()
- setIsDragOver(false)
- }
-
- const handleDrop = (e) => {
- e.preventDefault()
- e.stopPropagation()
- setIsDragOver(false)
-
- if (isUploading) return
-
- const files = Array.from(e.dataTransfer.files)
- if (files.length > 0 && validateFiles(files)) {
- simulateUpload(files)
- }
- }
-
- const clearUploadedFiles = () => {
- setUploadedFiles([])
- }
-
- const removeFile = (indexToRemove) => {
- setUploadedFiles(prev => prev.filter((_, index) => index !== indexToRemove))
- }
-
- const menuItems = [
- { id: 'home', label: '首页', icon: Home },
- { id: 'notebooks', label: '笔记管理', icon: BookOpen },
- {
- id: 'dashboard',
- label: '数据看板',
- icon: BarChart3,
- submenu: [
- { id: 'overview', label: '账号概况' },
- { id: 'content', label: '内容分析' },
- { id: 'fans', label: '粉丝数据' }
- ]
- },
- { id: 'activity', label: '活动中心', icon: Activity },
- { id: 'notes', label: '笔记灵感', icon: BookOpen },
- { id: 'creator', label: '创作学院', icon: Users },
- { id: 'journal', label: '创作日刊', icon: BookOpen }
- ]
- const toggleMenu = (menuId) => {
- setExpandedMenu(expandedMenu === menuId ? null : menuId)
- }
-
- // 新增:处理页面切换的函数
- const handlePageChange = (pageId) => {
- setActivePage(pageId)
- // 如果点击的是有子菜单的项目,也要展开子菜单
- const menuItem = menuItems.find(item => item.id === pageId)
- if (menuItem && menuItem.submenu) {
- setExpandedMenu(pageId)
- }
- }
-
- return (
- <div className="app">
- {/* Header */}
- <header className="header">
- <div className="header-left">
- <div className="logo">小红书</div>
- <h1 className="header-title">创作服务平台</h1>
- </div>
- <div className="header-right">
- <div className="user-info">
- <User size={16} />
- <span>小红薯63081EA1</span>
- </div>
- </div>
- </header>
-
- {/* Sidebar */}
- <aside className="sidebar">
- <button className="publish-btn">发布笔记</button>
- <nav className="nav-menu">
- {menuItems.map((item) => (
- <div key={item.id} className="nav-item">
- <a
- href="#"
- className={`nav-link ${activePage === item.id ? 'active' : ''}`}
- onClick={(e) => {
- e.preventDefault()
- if (item.submenu) {
- toggleMenu(item.id)
- } else {
- handlePageChange(item.id)
- }
- }}
- >
- <item.icon size={16} />
- <span>{item.label}</span>
- {item.submenu && <ChevronDown size={16} style={{ marginLeft: 'auto', transform: expandedMenu === item.id ? 'rotate(180deg)' : 'rotate(0deg)', transition: 'transform 0.3s ease' }} />}
- </a>
-
- {item.submenu && expandedMenu === item.id && (
- <div className="nav-submenu">
- {item.submenu.map((subItem) => (
- <a
- key={subItem.id}
- href="#"
- className={`nav-link ${activePage === subItem.id ? 'active' : ''}`}
- onClick={(e) => {
- e.preventDefault()
- handlePageChange(subItem.id)
- }}
- >
- {subItem.label}
- </a>
- ))}
- </div>
- )}
- </div>
- ))}
- </nav>
- </aside> {/* Main Content */}
- <main className="main-content">
- <div className="content-wrapper">
- {activePage === 'dashboard' || activePage === 'overview' || activePage === 'content' || activePage === 'fans' ? (
- // 上传页面内容(数据看板相关页面显示上传功能)
- <>
- {/* Upload Tabs */}
- <div className="upload-tabs">
- <button
- className={`upload-tab ${activeTab === 'video' ? 'active' : ''}`}
- onClick={() => setActiveTab('video')}
- >
- 上传视频
- </button>
- <button
- className={`upload-tab ${activeTab === 'image' ? 'active' : ''}`}
- onClick={() => setActiveTab('image')}
- >
- 上传图文
- </button>
- </div>
-
- {/* Upload Area */}
- <div
- className={`upload-area ${isDragOver ? 'drag-over' : ''}`}
- onDragOver={handleDragOver}
- onDragLeave={handleDragLeave}
- onDrop={handleDrop}
- >
- <div className="upload-icon">
- {activeTab === 'video' ? <Video /> : <Image />}
- </div>
- <h2 className="upload-title">
- {activeTab === 'video' ? '拖拽视频到此处或点击上传' : '拖拽图片到此处或点击上传'}
- </h2>
- <p className="upload-subtitle">
- {activeTab === 'video' ? '(需支持上传格式)' : '(需支持上传格式)'}
- </p>
- <button
- className={`upload-btn ${isUploading ? 'uploading' : ''}`}
- onClick={handleFileUpload}
- disabled={isUploading}
- >
- {isUploading ? `上传中... ${uploadProgress}%` : (activeTab === 'video' ? '上传视频' : '上传图片')}
- </button>
-
- {/* Upload Progress Bar */}
- {isUploading && (
- <div className="progress-container">
- <div className="progress-bar">
- <div
- className="progress-fill"
- style={{ width: `${uploadProgress}%` }}
- ></div>
- </div>
- <div className="progress-text">{uploadProgress}%</div>
- </div>
- )}
- </div>
-
- {/* File Preview Area */}
- {uploadedFiles.length > 0 && (
- <div className="file-preview-area">
- <div className="preview-header">
- <h3 className="preview-title">已上传文件 ({uploadedFiles.length})</h3>
- <button className="clear-files-btn" onClick={clearUploadedFiles}>
- 清除所有
- </button>
- </div>
- <div className="file-grid">
- {uploadedFiles.map((file, index) => (
- <div key={index} className="file-item">
- <button
- className="remove-file-btn"
- onClick={() => removeFile(index)}
- title="删除文件"
- >
- ×
- </button>
- {file.type?.startsWith('image/') ? (
- <div className="file-thumbnail">
- <img src={URL.createObjectURL(file)} alt={file.name} />
- </div>
- ) : (
- <div className="file-thumbnail video-thumbnail">
- <Video size={24} />
- </div>
- )}
- <div className="file-info">
- <div className="file-name" title={file.name}>
- {file.name.length > 20 ? file.name.substring(0, 17) + '...' : file.name}
- </div>
- <div className="file-size">
- {(file.size / 1024 / 1024).toFixed(2)} MB
- </div>
- </div>
- </div>
- ))}
- </div>
- </div>
- )}
-
- {/* Upload Info */}
- <div className="upload-info fade-in" key={activeTab}>
- {activeTab === 'image' ? (
- <>
- <div className="info-item">
- <h3 className="info-title">图片大小</h3>
- <p className="info-desc">
- 支持上传的图片大小,<br />
- 最大32MB的图片文件
- </p>
- </div>
- <div className="info-item">
- <h3 className="info-title">图片格式</h3>
- <p className="info-desc">
- 支持上传的图片格式:<br />
- 推荐使用png、jpg、jpeg、webp,不支持gif、live及其他转化的动图
- </p>
- </div>
- <div className="info-item">
- <h3 className="info-title">图片分辨率</h3>
- <p className="info-desc">
- 不要竖图片尺寸,推荐上传3:4尺寸之间,分辨率不低于720*960的图片,<br />
- 超过17张的时候图片将自动压缩至相配尺寸
- </p>
- </div>
- </>
- ) : (
- <>
- <div className="info-item">
- <h3 className="info-title">视频大小</h3>
- <p className="info-desc">
- 支持种类5分钟内视频,<br />
- 最大2GB的视频文件
- </p>
- </div>
- <div className="info-item">
- <h3 className="info-title">视频格式</h3>
- <p className="info-desc">
- 支持常用视频格式:<br />
- 推荐使用mp4、mov
- </p>
- </div>
- <div className="info-item">
- <h3 className="info-title">视频分辨率</h3>
- <p className="info-desc">
- 推荐上传720P (1280*720) 及以上视频,<br />
- 超过1080P的视频可能可能导致上传稍慢且消耗流量
- </p>
- </div>
- </>
- )}
- </div>
- </>
- ) : (
- // 其他页面的内容
- <div className="page-content">
- <div className="page-header">
- <h1 className="page-title">
- {activePage === 'home' && '首页'}
- {activePage === 'notebooks' && '笔记管理'}
- {activePage === 'activity' && '活动中心'}
- {activePage === 'notes' && '笔记灵感'}
- {activePage === 'creator' && '创作学院'}
- {activePage === 'journal' && '创作日刊'}
- </h1>
- </div>
- <div className="page-body">
- <div className="placeholder-content">
- <div className="placeholder-icon">
- {activePage === 'home' && <Home size={48} />}
- {activePage === 'notebooks' && <BookOpen size={48} />}
- {activePage === 'activity' && <Activity size={48} />}
- {activePage === 'notes' && <BookOpen size={48} />}
- {activePage === 'creator' && <Users size={48} />}
- {activePage === 'journal' && <BookOpen size={48} />}
- </div>
- <h3 className="placeholder-title">
- {activePage === 'home' && '欢迎来到小红书创作平台'}
- {activePage === 'notebooks' && '笔记管理功能开发中'}
- {activePage === 'activity' && '活动中心功能开发中'}
- {activePage === 'notes' && '笔记灵感功能开发中'}
- {activePage === 'creator' && '创作学院功能开发中'}
- {activePage === 'journal' && '创作日刊功能开发中'}
- </h3>
- <p className="placeholder-desc">
- {activePage === 'home' && '在这里您可以管理您的创作内容,查看数据分析,获取创作灵感。'}
- {activePage === 'notebooks' && '这里将显示您的所有笔记,支持编辑、删除、分类等操作。'}
- {activePage === 'activity' && '这里将展示最新的平台活动,让您参与更多有趣的创作活动。'}
- {activePage === 'notes' && '这里将为您提供创作灵感和写作建议,帮助您创作更好的内容。'}
- {activePage === 'creator' && '这里将提供创作技巧教学和平台规则说明,助您成为优秀创作者。'}
- {activePage === 'journal' && '这里将展示创作相关的最新资讯和平台动态。'}
- </p>
- </div>
- </div>
- </div>
- )}
- </div>
- </main>
- </div>
- )
-}
-
-export default App
diff --git a/xiaohongshu-upload-platform/src/index.css b/xiaohongshu-upload-platform/src/index.css
deleted file mode 100644
index 72c144a..0000000
--- a/xiaohongshu-upload-platform/src/index.css
+++ /dev/null
@@ -1,29 +0,0 @@
-* {
- margin: 0;
- padding: 0;
- box-sizing: border-box;
-}
-
-body {
- font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'PingFang SC', 'Hiragino Sans GB', 'Microsoft YaHei', sans-serif;
- -webkit-font-smoothing: antialiased;
- -moz-osx-font-smoothing: grayscale;
- background-color: #f5f7fa;
-}
-
-button {
- border: none;
- background: none;
- cursor: pointer;
- font-family: inherit;
-}
-
-a {
- text-decoration: none;
- color: inherit;
-}
-
-#root {
- width: 100%;
- min-height: 100vh;
-}
diff --git a/xiaohongshu-upload-platform/src/main.jsx b/xiaohongshu-upload-platform/src/main.jsx
deleted file mode 100644
index b9a1a6d..0000000
--- a/xiaohongshu-upload-platform/src/main.jsx
+++ /dev/null
@@ -1,10 +0,0 @@
-import { StrictMode } from 'react'
-import { createRoot } from 'react-dom/client'
-import './index.css'
-import App from './App.jsx'
-
-createRoot(document.getElementById('root')).render(
- <StrictMode>
- <App />
- </StrictMode>,
-)
diff --git a/xiaohongshu-upload-platform/vite.config.js b/xiaohongshu-upload-platform/vite.config.js
deleted file mode 100644
index 8b0f57b..0000000
--- a/xiaohongshu-upload-platform/vite.config.js
+++ /dev/null
@@ -1,7 +0,0 @@
-import { defineConfig } from 'vite'
-import react from '@vitejs/plugin-react'
-
-// https://vite.dev/config/
-export default defineConfig({
- plugins: [react()],
-})