pro-craft 0.1.12__py3-none-any.whl → 0.1.14__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of pro-craft might be problematic. Click here for more details.

@@ -1,113 +0,0 @@
1
-
2
- from mcp.server.fastmcp import Context, FastMCP, Icon
3
- from prompt_writing_assistant.file_manager import ContentManager, TextType
4
- from mcp.server.fastmcp import FastMCP
5
- from mcp.server.fastmcp.prompts import base
6
- from pydantic import BaseModel, Field
7
- from prompt_writing_assistant.prompt_helper import IntellectType,Intel
8
-
9
-
10
- content_manager = ContentManager()
11
- intels = Intel()
12
-
13
- mcp = FastMCP("Content")
14
-
15
- @mcp.prompt(title="Code Review")
16
- def review_code(code: str) -> str:
17
- return f"Please review this code:\n\n{code}"
18
-
19
-
20
- @mcp.prompt(title="Debug Assistant")
21
- def debug_error(error: str) -> list[base.Message]:
22
- return [
23
- base.UserMessage("I'm seeing this error:"),
24
- base.UserMessage(error),
25
- base.AssistantMessage("I'll help debug that. What have you tried so far?"),
26
- ]
27
-
28
-
29
- @mcp.tool()
30
- def save_content(text:str)->str:
31
- """
32
- text : 需要存储的内容
33
- return : 返回是否存储成功的信息
34
- """
35
- result =content_manager.save_content_auto(
36
- text = text)
37
- return result
38
-
39
- @mcp.tool()
40
- def similarit_content(text: str,limit: int):
41
- """
42
- text : 待查询的文字, 进行匹配
43
- limit : 查询的数量
44
- """
45
-
46
- result = content_manager.similarity(
47
- content = text,
48
- limit = limit
49
- )
50
- return result
51
-
52
- @mcp.tool()
53
- def get_prompts(prompt_id: str,version: str = "1.0"):
54
- """
55
- prompt_id : 待查询的文字, 进行匹配
56
- limit : 查询的数量
57
- """
58
- result = intels.get_prompts_from_sql(
59
- table_name = "prompts_data",
60
- prompt_id = prompt_id,
61
- version=version,
62
- )
63
- return result
64
-
65
- @mcp.tool()
66
- def list_cities() -> list[str]:
67
- """Get a list of cities"""
68
- return ["London", "Paris", "Tokyo"]
69
-
70
-
71
-
72
-
73
-
74
-
75
- class WeatherData(BaseModel):
76
- """Weather information structure."""
77
-
78
- temperature: float = Field(description="Temperature in Celsius")
79
- humidity: float = Field(description="Humidity percentage")
80
- condition: str
81
- wind_speed: float
82
-
83
-
84
- @mcp.tool() # icons=[icon]
85
- def get_weather(city: str) -> WeatherData:
86
- """Get weather for a city - returns structured data."""
87
- # Simulated weather data
88
- return WeatherData(
89
- temperature=22.5,
90
- humidity=45.0,
91
- condition="sunny",
92
- wind_speed=5.2,
93
- )
94
-
95
-
96
- from PIL import Image as PILImage
97
- from mcp.server.fastmcp import FastMCP, Image
98
-
99
- @mcp.tool()
100
- def create_thumbnail(image_path: str) -> Image:
101
- """Create a thumbnail from an image"""
102
- img = PILImage.open(image_path)
103
- img.thumbnail((100, 100))
104
- return Image(data=img.tobytes(), format="png")
105
-
106
-
107
-
108
- if __name__ == "__main__":
109
- mcp.run(transport="streamable-http")
110
- # mcp.run(transport="sse")
111
- # search_mcp.run(transport="sse", mount_path="/search")
112
-
113
-
@@ -1,33 +0,0 @@
1
- from mcp.server.fastmcp import FastMCP
2
-
3
-
4
- # region MCP Math
5
- mcp = FastMCP("Math")
6
-
7
- @mcp.tool(description="A simple add tool")
8
- def add(a: int, b: int) -> int:
9
- """Adds two integers.
10
- Args:
11
- a: The first integer.
12
- b: The second integer.
13
- """
14
- return a + b
15
-
16
-
17
- @mcp.tool()
18
- def multiply(a: int, b: int) -> int:
19
- """Multiply two integers.
20
- Args:
21
- a: The first integer.
22
- b: The second integer.
23
- """
24
- return a * b
25
- # endregion
26
-
27
-
28
- if __name__ == "__main__":
29
- mcp.run(transport="streamable-http")
30
- # mcp.run(transport="sse")
31
- # search_mcp.run(transport="sse", mount_path="/search")
32
-
33
-
@@ -1,35 +0,0 @@
1
-
2
- from mcp.server.fastmcp import Context, FastMCP
3
-
4
-
5
- # region MCP Math
6
- mcp = FastMCP("resource")
7
-
8
-
9
- @mcp.resource("config://settings")
10
- def get_settings() -> str:
11
- """Get application settings."""
12
- return """{
13
- "theme": "dark",
14
- "language": "en",
15
- "debug": false
16
- }"""
17
-
18
- @mcp.resource("file://documents/{name}")
19
- def read_document(name: str) -> str:
20
- """Read a document by name."""
21
- # This would normally read from disk
22
- path = "/Users/zhaoxuefeng/GitHub/prompt_writing_assistant/tests/temp_file/"
23
- path += name
24
- with open(path,'r') as f:
25
- return f.read()
26
-
27
- @mcp.resource("file://notes/{name}")
28
- def read_notes(name:str)-> str:
29
- """ 阅读备忘录"""
30
-
31
- return "你要做王子"
32
-
33
- if __name__ == "__main__":
34
- mcp.run(transport="streamable-http")
35
-
@@ -1,6 +0,0 @@
1
-
2
- # server
3
- from typing import Dict, Any, Optional, List
4
- from pydantic import BaseModel, Field, model_validator
5
-
6
-
@@ -1,283 +0,0 @@
1
- # server
2
- # 推荐算法
3
-
4
- from ..models import UpdateItem, DeleteResponse, DeleteRequest, QueryItem
5
- from fastapi import APIRouter, Depends, HTTPException, status
6
- from typing import Dict, Any
7
- from diglife.embedding_pool import EmbeddingPool
8
- from diglife.log import Log
9
- import os
10
- import httpx
11
-
12
- from dotenv import load_dotenv, find_dotenv
13
-
14
- dotenv_path = find_dotenv()
15
- load_dotenv(dotenv_path, override=True)
16
-
17
-
18
-
19
- router = APIRouter(tags=["recommended"])
20
-
21
- logger = Log.logger
22
-
23
- recommended_biographies_cache_max_leng = os.getenv("recommended_biographies_cache_max_leng",2) #config.get("recommended_biographies_cache_max_leng", 2)
24
- recommended_biographies_cache_max_leng = int(recommended_biographies_cache_max_leng)
25
- recommended_cache_max_leng = os.getenv("recommended_cache_max_leng",2) #config.get("recommended_cache_max_leng", 2)
26
- recommended_cache_max_leng = int(recommended_cache_max_leng)
27
- user_server_base_url = "http://182.92.107.224:7000"
28
-
29
- ep = EmbeddingPool()
30
- recommended_biographies_cache: Dict[str, Dict[str, Any]] = {}
31
- recommended_figure_cache: Dict[str, Dict[str, Any]] = {}
32
-
33
- @router.post(
34
- "/update", # 推荐使用POST请求进行数据更新
35
- summary="更新或添加文本嵌入",
36
- description="将给定的文本内容与一个ID关联并更新到Embedding池中。",
37
- response_description="表示操作是否成功。",
38
- )
39
- def recommended_update(item: UpdateItem):
40
- """记忆卡片是0 传记是1
41
- 记忆卡片是0
42
- 记忆卡片上传的是记忆卡片的内容 str
43
- 记忆卡片id
44
- 0
45
-
46
- 传记是1
47
- 上传的是传记简介 str
48
- 传记id
49
- 1
50
-
51
- 数字分身是2
52
- 上传数字分身简介和性格描述 str
53
- 数字分身id
54
- 2
55
- """
56
- # TODO 需要一个反馈状态
57
- try:
58
- if item.type in [0, 1, 2]: # 上传的是卡片
59
- ep.update(text=item.text, id=item.id, type=item.type)
60
- else:
61
- logger.error(f"Error updating EmbeddingPool for ID '{item.id}': {e}")
62
- raise HTTPException(
63
- status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
64
- detail=f"Failed to update embedding for ID '{item.id}': {e}",
65
- )
66
-
67
- return {"status": "success", "message": f"ID '{item.id}' updated successfully."}
68
-
69
- except ValueError as e: # 假设EmbeddingPool.update可能抛出ValueError
70
- logger.warning(f"Validation error during update: {e}")
71
- raise HTTPException(status_code=status.HTTP_400_BAD_REQUEST, detail=str(e))
72
- except Exception as e:
73
- logger.error(f"Error updating EmbeddingPool for ID '{item.id}': {e}")
74
- raise HTTPException(
75
- status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
76
- detail=f"Failed to update embedding for ID '{item.id}': {e}",
77
- )
78
-
79
-
80
- @router.post("/delete", response_model=DeleteResponse, description="delete")
81
- async def delete_server(request: DeleteRequest):
82
-
83
- logger.info("running delete_server")
84
-
85
- # TODO 需要一个反馈状态
86
- result = ep.delete(id=request.id) # 包裹的内核函数
87
-
88
- ########
89
- return DeleteResponse(
90
- status="success",
91
- )
92
-
93
-
94
-
95
-
96
- # async def aget_content_by_id(url = ""):
97
- # # url = url.format(user_profile_id = user_profile_id)
98
- # async with httpx.AsyncClient() as client:
99
- # try:
100
- # response = await client.get(url)
101
- # response.raise_for_status() # 如果状态码是 4xx 或 5xx,会抛出 HTTPStatusError 异常
102
-
103
- # print(f"Status Code: {response.status_code}")
104
- # print(f"Response Body: {response.json()}") # 假设返回的是 JSON
105
- # return response.json()
106
- # except httpx.HTTPStatusError as e:
107
- # print(f"HTTP error occurred: {e.response.status_code} - {e.response.text}")
108
- # except httpx.RequestError as e:
109
- # print(f"An error occurred while requesting {e.request.url!r}: {e}")
110
- # except Exception as e:
111
- # print(f"An unexpected error occurred: {e}")
112
- # return None
113
-
114
- async def aget_(url = ""):
115
- async with httpx.AsyncClient() as client:
116
- try:
117
- response = await client.get(url)
118
- response.raise_for_status() # 如果状态码是 4xx 或 5xx,会抛出 HTTPStatusError 异常
119
-
120
- print(f"Status Code: {response.status_code}")
121
- print(f"Response Body: {response.json()}") # 假设返回的是 JSON
122
- return response.json()
123
- except httpx.HTTPStatusError as e:
124
- print(f"HTTP error occurred: {e.response.status_code} - {e.response.text}")
125
- except httpx.RequestError as e:
126
- print(f"An error occurred while requesting {e.request.url!r}: {e}")
127
- except Exception as e:
128
- print(f"An unexpected error occurred: {e}")
129
- return None
130
-
131
- @router.post(
132
- "/search_biographies_and_cards",
133
- summary="搜索传记和记忆卡片",
134
- description="搜索传记和记忆卡片",
135
- response_description="搜索结果列表。",
136
- )
137
- async def recommended_biographies_and_cards(query_item: QueryItem):
138
- """
139
- # result = [
140
- # {
141
- # "id": "1916693308020916225", # 传记ID
142
- # "type": 1,
143
- # "order": 0,
144
- # },
145
- # {
146
- # "id": "1962459564012359682", # 卡片ID
147
- # "type": 0,
148
- # "order": 1,
149
- # },
150
- # {
151
- # "id": "1916389315373727745", # 传记ID
152
- # "type": 1,
153
- # "order": 2,
154
- # },
155
- # ]
156
-
157
- {
158
- "text":"这是一个传记001",
159
- "id":"1916693308020916225",
160
- "type":1
161
- }
162
- {
163
- "text":"这是一个传记002",
164
- "id":"1916389315373727745",
165
- "type":1
166
- }
167
- {
168
- "text":"这是一个卡片001",
169
- "id":"1962459564012359682",
170
- "type":0
171
- }
172
- """
173
- try:
174
- # TODO 需要一个通过id 获取对应内容的接口
175
- # TODO 调用id 获得对应的用户简介 query_item.user_id
176
-
177
-
178
- user_profile_id_to_fetch = query_item.user_id
179
- # memory_info = await aget_content_by_id(user_profile_id_to_fetch,url = user_server_base_url + "/api/inner/getMemoryCards?userProfileId={user_profile_id}")
180
- memory_info = await aget_(url = user_server_base_url + f"/api/inner/getMemoryCards?userProfileId={user_profile_id_to_fetch}")
181
- # memory_info = await get_memorycards_by_id(user_profile_id_to_fetch)
182
- user_brief = '\n'.join([i.get('content') for i in memory_info['data']["memoryCards"][:4]])
183
-
184
-
185
- result = ep.search_bac(query=user_brief)
186
-
187
- if recommended_biographies_cache.get(query_item.user_id):
188
- clear_result = [
189
- i
190
- for i in result
191
- if i.get("id")
192
- not in recommended_biographies_cache.get(query_item.user_id)
193
- ]
194
- else:
195
- recommended_biographies_cache[query_item.user_id] = []
196
- clear_result = result
197
-
198
- recommended_biographies_cache[query_item.user_id] += [
199
- i.get("id") for i in result
200
- ]
201
- recommended_biographies_cache[query_item.user_id] = list(
202
- set(recommended_biographies_cache[query_item.user_id])
203
- )
204
- if (
205
- len(recommended_biographies_cache[query_item.user_id])
206
- > recommended_biographies_cache_max_leng
207
- ):
208
- recommended_biographies_cache[query_item.user_id] = []
209
-
210
- return {
211
- "status": "success",
212
- "result": clear_result,
213
- "query": query_item.user_id,
214
- }
215
-
216
- except Exception as e:
217
- logger.error(
218
- f"Error searching EmbeddingPool for query '{query_item.user_id}': {e}"
219
- )
220
- raise HTTPException(
221
- status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
222
- detail=f"Failed to perform search: {e}",
223
- )
224
-
225
-
226
-
227
- @router.post(
228
- "/search_figure_person",
229
- description="搜索数字分身的",
230
- )
231
- async def recommended_figure_person(query_item: QueryItem):
232
- """
233
-
234
- """
235
- try:
236
-
237
- user_profile_id_to_fetch = query_item.user_id
238
- # avatar_info = await aget_avatar_desc_by_id(user_profile_id_to_fetch)
239
- # avatar_info = await aget_content_by_id(user_profile_id_to_fetch,url = user_server_base_url + "/api/inner/getAvatarDesc?userProfileId={user_profile_id}")
240
- avatar_info = await aget_(url = user_server_base_url + f"/api/inner/getAvatarDesc?userProfileId={user_profile_id_to_fetch}")
241
- print(avatar_info,'avatar_info')
242
- if avatar_info["code"] == 200:
243
- user_brief = avatar_info["data"].get("avatarDesc")
244
- else:
245
- user_brief = "这是一个简单的人"
246
-
247
- result = ep.search_figure_person(query=user_brief) # 100+
248
-
249
- if recommended_figure_cache.get(query_item.user_id):
250
- # 不需要创建
251
- clear_result = [
252
- i
253
- for i in result
254
- if i.get("id") not in recommended_figure_cache.get(query_item.user_id)
255
- ]
256
- else:
257
- recommended_figure_cache[query_item.user_id] = []
258
- clear_result = result
259
-
260
- recommended_figure_cache[query_item.user_id] += [i.get("id") for i in result]
261
- recommended_figure_cache[query_item.user_id] = list(
262
- set(recommended_figure_cache[query_item.user_id])
263
- )
264
- if (
265
- len(recommended_figure_cache[query_item.user_id])
266
- > recommended_cache_max_leng
267
- ):
268
- recommended_figure_cache[query_item.user_id] = []
269
- return {
270
- "status": "success",
271
- "result": clear_result,
272
- "query": query_item.user_id,
273
- }
274
-
275
- except Exception as e:
276
- logger.error(
277
- f"Error searching EmbeddingPool for query '{query_item.user_id}': {e}"
278
- )
279
- raise HTTPException(
280
- status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
281
- detail=f"Failed to perform search: {e}",
282
- )
283
-
pro_craft/server.py DELETED
@@ -1,100 +0,0 @@
1
-
2
- from fastapi import FastAPI, HTTPException, Header
3
- from fastapi.middleware.cors import CORSMiddleware
4
- from pydantic import BaseModel, Field, model_validator
5
- import argparse
6
- import uvicorn
7
- from .log import Log
8
-
9
- default=8008
10
-
11
- app = FastAPI(
12
- title="LLM Service",
13
- description="Provides an OpenAI-compatible API for custom large language models.",
14
- version="1.0.1",
15
- )
16
-
17
- # --- Configure CORS ---
18
- origins = [
19
- "*", # Allows all origins (convenient for development, insecure for production)
20
- # Add the specific origin of your "别的调度" tool/frontend if known
21
- # e.g., "http://localhost:5173" for a typical Vite frontend dev server
22
- # e.g., "http://127.0.0.1:5173"
23
- ]
24
-
25
- app.add_middleware(
26
- CORSMiddleware,
27
- allow_origins=origins, # Specifies the allowed origins
28
- allow_credentials=True, # Allows cookies/authorization headers
29
- allow_methods=["*"], # Allows all methods (GET, POST, OPTIONS, etc.)
30
- allow_headers=["*"], # Allows all headers (Content-Type, Authorization, etc.)
31
- )
32
- # --- End CORS Configuration ---
33
-
34
-
35
- @app.get("/")
36
- async def root():
37
- """ x """
38
- return {"message": "LLM Service is running."}
39
-
40
-
41
- if __name__ == "__main__":
42
-
43
- parser = argparse.ArgumentParser(
44
- description="Start a simple HTTP server similar to http.server."
45
- )
46
- parser.add_argument(
47
- 'port',
48
- metavar='PORT',
49
- type=int,
50
- nargs='?', # 端口是可选的
51
- default=default,
52
- help=f'Specify alternate port [default: {default}]'
53
- )
54
- # 创建一个互斥组用于环境选择
55
- group = parser.add_mutually_exclusive_group()
56
-
57
- # 添加 --dev 选项
58
- group.add_argument(
59
- '--dev',
60
- action='store_true', # 当存在 --dev 时,该值为 True
61
- help='Run in development mode (default).'
62
- )
63
-
64
- # 添加 --prod 选项
65
- group.add_argument(
66
- '--prod',
67
- action='store_true', # 当存在 --prod 时,该值为 True
68
- help='Run in production mode.'
69
- )
70
- args = parser.parse_args()
71
-
72
- if args.prod:
73
- env = "prod"
74
- else:
75
- # 如果 --prod 不存在,默认就是 dev
76
- env = "dev"
77
-
78
- port = args.port
79
- if env == "dev":
80
- port += 100
81
- Log.reset_level('debug',env = env)
82
- reload = True
83
- app_import_string = f"{__package__}.server:app" # <--- 关键修改:传递导入字符串
84
- elif env == "prod":
85
- Log.reset_level('info',env = env)# ['debug', 'info', 'warning', 'error', 'critical']
86
- reload = False
87
- app_import_string = app
88
- else:
89
- reload = False
90
- app_import_string = app
91
-
92
-
93
- # 使用 uvicorn.run() 来启动服务器
94
- # 参数对应于命令行选项
95
- uvicorn.run(
96
- app_import_string,
97
- host="0.0.0.0",
98
- port=port,
99
- reload=reload # 启用热重载
100
- )
@@ -1,24 +0,0 @@
1
- pro_craft/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
2
- pro_craft/database.py,sha256=5dV-h9dVaS6euHLCtf0gYfq2pchl2QFdb2PEM4gTEU4,8740
3
- pro_craft/designer.py,sha256=3gyCqrjcw61sHzDjUPKhL1LOAE8xWLLbNT8NlK2mFLc,4739
4
- pro_craft/evals.py,sha256=1T86jur4k3cLk43j1GyAW4JS0nPNfl6P0ZOQmu-SgpA,1928
5
- pro_craft/file_manager.py,sha256=2j7lCt9L4mtvAy8_76ibTthXLwKKmVatWIB3DSvQM7U,3805
6
- pro_craft/log.py,sha256=MZf9jCZsiRoAq8v4FxVnJqeSXxgzAiiKf7mxz6bFtwM,4263
7
- pro_craft/prompt_helper.py,sha256=GClPsomdGdo6FXlp8VdiQy8GaBtj3oLeq2oFw0RiM3k,26592
8
- pro_craft/prompt_helper_async.py,sha256=-EtwjDUL2Xoi4qjZpzgnUyAVBkt-WCocGgVl5PgA4Js,27771
9
- pro_craft/prompt_helper_new.py,sha256=DV871XElJmHDO2xis1mC1f3QFvq3ll81VGGD9aj0Eiw,23542
10
- pro_craft/server.py,sha256=fPAosQIU0d7gxICiALl8u6QwbLI4cawVFyoRYebRES0,2827
11
- pro_craft/utils.py,sha256=cpvwk68mD9hYY8WCq2JXzfrrXqpshiscz_OSav4tC7U,5687
12
- pro_craft/code_helper/coder.py,sha256=NXglF1KiPtGe4HZN0MZvFJ8p9Iyd5kzIt72DQGgRwXA,24715
13
- pro_craft/server/__main__.py,sha256=LDTERPMe7RKj3eifVRo9aO9fNXdd16W5Hzr1APd04T0,4227
14
- pro_craft/server/models.py,sha256=CiUK8e73Bl7fo7ZbnwNTLYLeD4pb1fHMzWR13d3Y6vs,112
15
- pro_craft/server/mcp/__init__.py,sha256=4dbl-lFcm0r2tkOP04OxqiZG2jR-rqF181qi2AfU6UA,123
16
- pro_craft/server/mcp/content.py,sha256=DombC1DlasvEl_lzy4u6soVR7rxgmyWFlaEvTSdCiOU,2745
17
- pro_craft/server/mcp/math.py,sha256=OOzGXx64nK4bOVlu33PtVddcCQ9ilqA3Em9yxjSX9cg,641
18
- pro_craft/server/mcp/resource.py,sha256=z94jP3qZofO-1lZCM3TuOfLajw41HARs1ojXab1ymas,776
19
- pro_craft/server/mcp/weather.py,sha256=RAGuf4sgjlTQSfRRZ1Fo18JnuMQRS_Db9p6AqBQrl8E,455
20
- pro_craft/server/router/recommended.py,sha256=IAZFdmb8HSl2_TOJeuv5uOKIX47XyX4p4sEwxG-0vt0,9968
21
- pro_craft-0.1.12.dist-info/METADATA,sha256=VKEqBoEWYaOP0Ue2BSZ3iKZ1W_MYqsaRS7f3lQ-bscs,1800
22
- pro_craft-0.1.12.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
23
- pro_craft-0.1.12.dist-info/top_level.txt,sha256=yqYDHArnYMWpeCxkmGRwlL6sJtxiOUnYylLDx9EOgFg,10
24
- pro_craft-0.1.12.dist-info/RECORD,,
File without changes