feat: them tool CRUD MongoDB, file .env.example va huong dan su dung

parent 365713aa
GITLAB_URL=https://gitlab.meu-solutions.com # hoặc self-hosted
GITLAB_TOKEN=glpat-xxxxxxxxxxxxxxxxxxxx # PAT của cậu
QDRANT_HOST=localhost #192.168.0.29
QDRANT_PORT=7333
# Cấu hình cho MongoDB
MONGO_URI=mongodb://localhost:27017/
MONGO_DB_NAME=meu_rca
\ No newline at end of file
......@@ -150,13 +150,25 @@ User ←→ ProjectMember ←→ Project
Tất cả các bước trên **phải được thực hiện tự động**, không được hỏi lại người dùng "có cần gọi tool không" hoặc "nhắc project_id".
## 7. Filter Structure for Agent
## 7. MongoDB Tool Usage Rules (Bắt buộc tuân thủ khi thao tác DB)
Bạn có quyền truy cập các tools MongoDB (select, insert, update, delete) để tương tác trực tiếp với dữ liệu của project. Tuy nhiên, đây là thao tác rủi ro cao, bắt buộc tuân thủ:
- **Định dạng JSON:** Mọi tham số `query`, `document`, hoặc `update_data` phải là chuỗi JSON hợp lệ.
- **Tự động hóa an toàn:** Server đã tự động inject `project_id` vào mọi query. Bạn không cần (và không thể) sửa data của project khác. Server cũng tự động quản lý các trường `created_at`, `updated_at`, `is_deleted`. Không cần tự sinh các trường này khi insert.
- **Trường hợp _id:** Nếu cần query theo ID, chỉ cần truyền string (VD: `{"_id": "69b91..."}`). Server sẽ tự động parse sang `ObjectId`.
- **Quy trình bắt buộc trước khi Sửa/Xóa:** 1. Bắt buộc gọi `select_mongo_documents` để đọc bản ghi mục tiêu.
2. Báo cáo lại cho người dùng dữ liệu sắp bị ảnh hưởng.
3. Chỉ gọi `update_mongo_document` hoặc `delete_mongo_document` khi chắc chắn đúng `_id`.
- **Cơ chế Soft Delete:** Khi gọi `delete_mongo_document`, dữ liệu không mất đi mà chỉ được cập nhật cờ `is_deleted = True`. CẤM truyền query rỗng `{}` khi gọi hàm xóa.
## 8. Filter Structure for Agent
- Chỉ index files: *.ts, *.tsx, *.md, *.json, *.prisma
- Ưu tiên folders: src/app, src/lib, src/modules
- Tránh index: node_modules/, .next/, public/
- Max content length per file: 2000 chars (để tránh token overflow)
## 8. Configuration Files
## 9. Configuration Files
- next.config.js - Next.js configuration
- tsconfig.json - TypeScript configuration
- tailwind.config.ts - Tailwind CSS configuration
......@@ -165,13 +177,13 @@ Tất cả các bước trên **phải được thực hiện tự động**, kh
- Dockerfile - Container build instructions
- prisma/schema.prisma - Database schema
## 9. Build & Deployment
## 10. Build & Deployment
- Build scripts: build.bat (Windows), build.sh (Unix/Linux)
- Docker support: Containerized deployment with docker-compose
- Database: MongoDB setup via scripts/setup-mongodb.js
- Environment: Requires .env file with DB connection and secrets
## 10. Documentation References
## 11. Documentation References
- README.md - Project overview
- FEATURES.md - Feature documentation
- AUTHENTICATION.md - Auth implementation details
......@@ -181,11 +193,11 @@ Tất cả các bước trên **phải được thực hiện tự động**, kh
- req.txt - Requirements specification
- CODE_STRUCTURE.md - Detailed code structure documentation
## 11. Last Updated
## 12. Last Updated
- Updated: 2026-02-21
- Next review: Sau khi implement authentication features
- Status: Active development - RCA detection & insights features in progress
## 12. External Knowledge Base (NotebookLM)
## 13. External Knowledge Base (NotebookLM)
- NotebookLM link: [https://notebooklm.google.com/notebook/85ee5d70-5839-4de5-a5de-5a2d74d64b31] (cập nhật link thật)
- Khi cần context từ docs, design spec, hoặc requirement không có trong codebase/Qdrant:
- Truy vấn NotebookLM trước (copy-paste query vào NotebookLM chat).
......
Hướng dẫn chạy project meu-fastmcp
B1: Bật Docker (chạy database Qdrant ngầm) (chỉ làm bước 1 và 5 từ lần chạy thứ 2)
docker-compose -f docker-compose.infra.yml up -d (chỉ làm trong lần chạy đầu tiên những lần sau bật Docker Desktop lên thôi)
B2: Bật môi trường ảo (Thường chỉ làm trong lần chạy đầu tiên):
python -m venv venv
.\venv\Scripts\activate
B3: Cài các thư viện cần thiết (chỉ làm trong lần chạy đầu tiên):
pip install -r requirements.txt
B4: Cấu hình biến môi trường (.env) (chỉ làm trong lần chạy đầu tiên)
GITLAB_URL=https://gitlab.meu-solutions.com # hoặc self-hosted
GITLAB_TOKEN=glpat-xxxxxxxxxxx # tìm hoặc tạo mới trên gitlab
QDRANT_HOST=localhost #192.168.0.29
QDRANT_PORT=7333
# cấu hình cho MongoDB
MONGO_URI=mongodb://localhost:27017/
MONGO_DB_NAME=meu_rca
B5: Chạy Server:
python memory_mcp_server.py
Server sẽ chạy ở http://localhost:8090. Bạn có thể mở Swagger UI tại http://localhost:8090/docs để test thử các API.
Hướng Dẫn Kết Nối MEU MCP Server Từ Các Project Khác
Tài liệu này hướng dẫn cách kết nối AI Agent Cline từ một thư mục dự án bất kỳ tới MEU FastMCP Memory Server để sử dụng các công cụ thao tác với Vector DB (Qdrant) và MongoDB.
1. Yêu cầu chuẩn bị (Prerequisites)
Trước khi các project khác có thể kết nối, đảm bảo rằng Server MCP đang ở trạng thái sẵn sàng:
• Các service Database (MongoDB, Qdrant) đã được khởi động qua Docker (docker-compose up -d).
• Lưu ý: Không cần phải gõ lệnh python memory_mcp_server_stdio.py chạy ngầm. Bản thân AI Client sẽ tự động gọi file này thông qua giao thức stdio khi kết nối.
2. Cấu hình AI Client Cline
Tại thư mục của project mới (project client), bạn cần chỉ định cho AI Agent biết vị trí của MCP Server.
Dành cho Cline / Roo Code (VS Code):
1. Nhấn Ctrl + Shift + P -> Gõ Open MCP Settings.
2. Dán cấu hình sau vào file cline_mcp_settings.json (Thay đổi đường dẫn cho phù hợp):
JSON
{
"mcpServers": {
"multi-project-memory": {
"command": "D:\\Thuc tap\\MEU\\10-03-26\\MCP Server\\meu-fastmcp\\venv\\Scripts\\python.exe",
"args": [
"D:\\Thuc tap\\MEU\\10-03-26\\MCP Server\\meu-fastmcp\\memory_mcp_server_stdio.py"
]
}
}
}
Giải thích: Cần trỏ thẳng command vào python.exe bên trong thư mục venv của server để AI có đủ các thư viện (pymongo, fastmcp...).
3. Thiết lập Môi trường & Luật cho AI
Để AI Agent từ project mới thao tác an toàn và kết nối đúng DB, hãy làm 2 việc tại thư mục gốc của project mới:
Cấp biến môi trường: Copy file .env từ project MCP Server và dán vào thư mục gốc của project mới. Điều này giúp AI đọc được MONGO_URI và QDRANT_HOST.
Nếu bạn chạy MongoDB và Qdrant ở server khác, hãy tạo file .env dựa theo mẫu .env.example nhé.
Cấp Sổ tay Nghiệp vụ (AGENT.md): Tạo file AGENT.md ở project mới và đưa vào các quy tắc bắt buộc sau để chống AI "ảo giác":
# MCP & Database Usage Rules
Bạn đang được kết nối với hệ thống MEU MCP Server. Bắt buộc tuân thủ các quy tắc sau:
1. **Với MongoDB (CRUD):**
- Chỉ sử dụng định dạng chuỗi JSON hợp lệ cho các tham số.
- BẮT BUỘC gọi `select_mongo_documents` trước để xác nhận dữ liệu mục tiêu rồi mới được gọi `update` hoặc `delete`.
- Cấm truyền query rỗng `{}` khi dùng lệnh xóa. Cấm tự ý sinh ID khi insert (để DB tự sinh).
- Server đã tự động quản lý `project_id`, `created_at`, `updated_at` và cơ chế xóa mềm (`is_deleted`).
2. **Với Qdrant (Ngữ cảnh):**
- Dùng `save_context` để lưu kiến trúc hoặc logic quan trọng.
- Dùng `search_context` khi cần tìm hiểu về các hàm đã có trước khi viết code mới.
4. Danh sách các Tools hỗ trợ
Sau khi kết nối, AI sẽ tự động nhận diện 11 tools chia làm 2 nhóm chính:
• Nhóm Vector Memory (Qdrant): save_context, search_context, load_agent_context, index_gitlab_repo, list_all_keys, delete_context, delete_project_context.
• Nhóm Database (MongoDB): select_mongo_documents, insert_mongo_document, update_mongo_document, delete_mongo_document.
\ No newline at end of file
......@@ -3,6 +3,10 @@ import pathlib
import uuid
from datetime import datetime
import argparse
import json
import ast
from bson.objectid import ObjectId
from pymongo import MongoClient
from dotenv import load_dotenv
from fastmcp import FastMCP
......@@ -30,6 +34,20 @@ COLLECTION_NAME = os.getenv("QDRANT_COLLECTION", "multi_project_memory")
GITLAB_URL = os.getenv("GITLAB_URL", "")
GITLAB_TOKEN = os.getenv("GITLAB_TOKEN", "")
MONGO_URI = os.getenv("MONGO_URI", "mongodb://localhost:27017/")
MONGO_DB_NAME = os.getenv("MONGO_DB_NAME", "meu_rca")
mongo_client = None
mongo_db = None
if MONGO_URI:
try:
mongo_client = MongoClient(MONGO_URI, serverSelectionTimeoutMS=5000)
mongo_db = mongo_client[MONGO_DB_NAME]
# Ping thử để đảm bảo kết nối
mongo_client.admin.command('ping')
except Exception as e:
print(f"Lỗi kết nối MongoDB: {e}")
# MCP server
mcp = FastMCP(name="multi-project-memory")
......@@ -219,5 +237,102 @@ def delete_project_context(project_id: str):
)
return f"Deleted all contexts for project '{project_id}'"
# CÁC TOOL THAO TÁC VỚI MONGODB (AN TOÀN)
def parse_json_safe(data_str: str) -> dict:
try:
return json.loads(data_str)
except Exception:
return ast.literal_eval(data_str)
@mcp.tool()
def select_mongo_documents(project_id: str, collection_name: str, query: str = "{}", limit: int = 5) -> str:
"""Lấy dữ liệu từ MongoDB. An toàn: Tự động filter theo project_id, bỏ qua dữ liệu đã xóa mềm."""
if mongo_db is None: return "Lỗi: MongoDB chưa kết nối."
try:
query_dict = parse_json_safe(query)
query_dict["project_id"] = project_id
query_dict["is_deleted"] = {"$ne": True}
if "_id" in query_dict and isinstance(query_dict["_id"], str):
query_dict["_id"] = ObjectId(query_dict["_id"])
safe_limit = min(max(1, limit), 20)
results = list(mongo_db[collection_name].find(query_dict).limit(safe_limit))
for doc in results:
if "_id" in doc: doc["_id"] = str(doc["_id"])
return json.dumps(results, indent=2, ensure_ascii=False)
except Exception as e:
return f"Lỗi truy vấn: {str(e)}"
@mcp.tool()
def insert_mongo_document(project_id: str, collection_name: str, document: str) -> str:
"""Thêm document mới. An toàn: Tự động gán project_id và created_at."""
if mongo_db is None: return "Lỗi: MongoDB chưa kết nối."
try:
doc_dict = parse_json_safe(document)
if not isinstance(doc_dict, dict): return "Lỗi: Document phải là JSON object."
doc_dict["project_id"] = project_id
doc_dict["created_at"] = datetime.now().isoformat()
doc_dict["updated_at"] = doc_dict["created_at"]
doc_dict["is_deleted"] = False
result = mongo_db[collection_name].insert_one(doc_dict)
return f"Thêm thành công! Inserted ID: {str(result.inserted_id)}"
except Exception as e:
return f"Lỗi khi insert: {str(e)}"
@mcp.tool()
def update_mongo_document(project_id: str, collection_name: str, document_id: str, update_data: str) -> str:
"""Cập nhật document. An toàn: Chỉ cho phép update bằng document_id chính xác."""
if mongo_db is None: return "Lỗi: MongoDB chưa kết nối."
try:
update_dict = parse_json_safe(update_data)
update_dict.pop("project_id", None)
update_dict.pop("_id", None)
update_dict["updated_at"] = datetime.now().isoformat()
query = {
"_id": ObjectId(document_id),
"project_id": project_id,
"is_deleted": {"$ne": True}
}
formatted_update = {"$set": update_dict} if "$set" not in update_dict else update_dict
result = mongo_db[collection_name].update_one(query, formatted_update)
if result.matched_count == 0:
return "Không tìm thấy document hoặc bạn không có quyền sửa document này."
return "Cập nhật thành công!"
except Exception as e:
return f"Lỗi khi update: {str(e)}"
@mcp.tool()
def delete_mongo_document(project_id: str, collection_name: str, document_id: str) -> str:
"""Xóa document. An toàn: Dùng cơ chế Soft Delete (cập nhật cờ is_deleted), bảo vệ dữ liệu gốc."""
if mongo_db is None: return "Lỗi: MongoDB chưa kết nối."
try:
query = {
"_id": ObjectId(document_id),
"project_id": project_id
}
soft_delete_update = {
"$set": {
"is_deleted": True,
"deleted_at": datetime.now().isoformat()
}
}
result = mongo_db[collection_name].update_one(query, soft_delete_update)
if result.matched_count == 0:
return "Không tìm thấy document hợp lệ để xóa."
return "Đã xóa (mềm) thành công document."
except Exception as e:
return f"Lỗi khi xóa: {str(e)}"
if __name__ == "__main__":
mcp.run()
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment