Skip to content

Commit f624971

Browse files
Dt8333aider-chat-botSoulter
authored
chore: fix bunches of type checking errors (#3213)
* chore(core.utils): 🚨 修正错误Lint * chore(core.provider): 🚨 修复基类错误Lint * chore(core.utils): 补全session_get()的重载 * chore(core.provider): 🚨 修正实现错误Lint * chore(core.platform): 🚨 修正platform基类和webchat的错误Lint * chore(core.platform): 修正错误实现Lint * fix(core.provider): 修复循环调用和错误assert * chore(core.platform): 修复部分实现Lint * chore(core.provider): 补充Dify.text_chat_stream的参数类型 * chore(core.pipeline): 🚨 修复错误Lint * fix(core.slack): 补充遗漏导入 * chore(core.utils): 修复错误的session_get声明 * chore(core.platform): 移除Lark adapter import中的wildcard * chore(core.db): 修复声明和部分逻辑 * chore(core.db): 添加typings,使faiss参数能被正确识别。 * chore(core): 修复声明 * chore(core): 修改声明 * chore: 补充faiss声明 * chore(dashboard): 修改实现,减少报错 * chore(package): 修改部分声明与实现,减少报错 * chore(core): 添加Handler的overload,以去除部分assert同时通过类型检查 * chore(core.pipeline): 修改Pipeline Scheduler的execute,将判断属性改为判断类型,通过静态类型检查 * chore(core.config): 添加类型标注,通过类型检查 * chore(core.message): 为File._download_file添加检查,通过类型检查 * fix: 将断言改为条件判断以实现优雅关闭的容错性 * refactor: 移除 discord 客户端中的 assert,改用 if None 判断并抛出异常 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * fix: DiscordPlatformAdapter 对 self.client.user 为 None 做日志并返回,移除断言 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * fix: 增强 Lark 相关空值/异常检查并完善日志输出 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * refactor: 将断言替换为条件检查并加入日志与错误处理 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * chore: 移除LLM生成的无用注释 * refactor: 使用 File.get_file 替换下载逻辑并移除 assert,提供默认 filename Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * fix: Slack Socket 未初始化抛出运行时异常,图片 URL 判空改为非空判断 * refactor: 将 WeChatPadProAdapter 的断言改为空值判断并添加日志 * refactor: 使用 isinstance 替代断言实现类型判断,便于静态检查 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * fix: 去除cast,直接使用字段与字典访问,修正端口解析 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * refactor: 使用 match-case 重构 ProviderManager 加载并通过类型检查抛出 TypeError Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * fix: group_name_display 时若 group 对象为空则记录错误并返回 * fix: 将 _get_current_persona_id 的 assert 替换成 if guard 并返回 None Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * fix: 优化插件目录存在性检查及图片URL非空验证,更新JSON排序配置 * fix: 将 datetime_str 的 assert 替换为显式检查并抛出异常 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * refactor: 移除 cast,改为运行时检查并在找不到调度器时跳过 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * refactor: 移除 cast,改用 isinstance 检查 FaissVecDB 并警告 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * fix: 删除 typing.cast 导入,并在获取文件绝对路径前校验 file_ * refactor: 移除 typing.cast,简化内容安全检查调用 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * refactor: 将 PlatformMetadata.id 设为必填并在注册时传入 id,移除 cast * refactor: 移除 cast,改用 HasInitialize 与 isinstance 进行初始化 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * fix: 为 ProviderManager.initialize 增加ID类型判断,避免 None 导致 get 失败 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * refactor: 为 OTTSProvider 与 AzureNativeProvider 引入 _client 与 client 属性改进上下文管理 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * fix: 为 Whisper 自托管源添加模型未初始化校验并直接调用 transcribe Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * refactor: 移除未使用的 cast 导入并简化 platform_name 赋值 * refactor: 引入 cast 并对 id 使用 cast(str, ...) 提升类型安全 * fix: 将 _id_to_sid 返回改为 str,空值返回空串;对 id 与 message_id 使用 cast Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * refactor: 重构 Discord 处理逻辑:强制 类型转换、优先斜杠指令并优化提及判断 Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * fix: 统一对 id 获取执行 cast,并在微信消息解析失败时抛错 * Revert "fix: 去除cast,直接使用字段与字典访问,修正端口解析" This reverts commit 1cbfdf9. * fix: 百炼 Rerank 会话关闭时返回空结果;初始化 request.prompt 避免空值拼接 * fix: 统一处理搜索结果链接为字符串,新增 _get_url 助手并适配 Bing/Sogo Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> * refactor: 调整 call_handler 泛型、Discord 通道注解及 FishAudioTTS API 请求类型 * refactor: 使用 col(...) 替代列引用并对结果进行 CursorResult 强转 * chore: ruff format --------- Co-authored-by: aider (openai/gemini-3-pro-high) <aider@aider.chat> Co-authored-by: Soulter <905617992@qq.com>
1 parent aa6d07a commit f624971

File tree

96 files changed

+1221
-527
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

96 files changed

+1221
-527
lines changed

astrbot/core/agent/runners/tool_loop_agent_runner.py

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,6 @@ async def step(self):
9797
llm_resp_result = None
9898

9999
async for llm_response in self._iter_llm_responses():
100-
assert isinstance(llm_response, LLMResponse)
101100
if llm_response.is_chunk:
102101
if llm_response.result_chain:
103102
yield AgentResponse(

astrbot/core/agent/tool.py

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
from collections.abc import Awaitable, Callable
1+
from collections.abc import AsyncGenerator, Awaitable, Callable
22
from typing import Any, Generic
33

44
import jsonschema
@@ -7,6 +7,8 @@
77
from pydantic import Field, model_validator
88
from pydantic.dataclasses import dataclass
99

10+
from astrbot.core.message.message_event_result import MessageEventResult
11+
1012
from .run_context import ContextWrapper, TContext
1113

1214
ParametersType = dict[str, Any]
@@ -38,7 +40,10 @@ def validate_parameters(self) -> "ToolSchema":
3840
class FunctionTool(ToolSchema, Generic[TContext]):
3941
"""A callable tool, for function calling."""
4042

41-
handler: Callable[..., Awaitable[Any]] | None = None
43+
handler: (
44+
Callable[..., Awaitable[str | None] | AsyncGenerator[MessageEventResult, None]]
45+
| None
46+
) = None
4247
"""a callable that implements the tool's functionality. It should be an async function."""
4348

4449
handler_module_path: str | None = None

astrbot/core/astr_agent_tool_exec.py

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -185,7 +185,11 @@ async def _execute_mcp(
185185

186186
async def call_local_llm_tool(
187187
context: ContextWrapper[AstrAgentContext],
188-
handler: T.Callable[..., T.Awaitable[T.Any]],
188+
handler: T.Callable[
189+
...,
190+
T.Awaitable[MessageEventResult | mcp.types.CallToolResult | str | None]
191+
| T.AsyncGenerator[MessageEventResult | CommandResult | str | None, None],
192+
],
189193
method_name: str,
190194
*args,
191195
**kwargs,

astrbot/core/config/astrbot_config.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,10 @@ class AstrBotConfig(dict):
2424
- 如果传入了 schema,将会通过 schema 解析出 default_config,此时传入的 default_config 会被忽略。
2525
"""
2626

27+
config_path: str
28+
default_config: dict
29+
schema: dict | None
30+
2731
def __init__(
2832
self,
2933
config_path: str = ASTRBOT_CONFIG_PATH,

astrbot/core/core_lifecycle.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -197,7 +197,7 @@ def _load(self) -> None:
197197
# 把插件中注册的所有协程函数注册到事件总线中并执行
198198
extra_tasks = []
199199
for task in self.star_context._register_tasks:
200-
extra_tasks.append(asyncio.create_task(task, name=task.__name__))
200+
extra_tasks.append(asyncio.create_task(task, name=task.__name__)) # type: ignore
201201

202202
tasks_ = [event_bus_task, *extra_tasks]
203203
for task in tasks_:

astrbot/core/db/__init__.py

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,7 @@
55
from dataclasses import dataclass
66

77
from deprecated import deprecated
8-
from sqlalchemy.ext.asyncio import AsyncSession, create_async_engine
9-
from sqlalchemy.orm import sessionmaker
8+
from sqlalchemy.ext.asyncio import AsyncSession, async_sessionmaker, create_async_engine
109

1110
from astrbot.core.db.po import (
1211
Attachment,
@@ -32,7 +31,7 @@ def __init__(self) -> None:
3231
echo=False,
3332
future=True,
3433
)
35-
self.AsyncSessionLocal = sessionmaker(
34+
self.AsyncSessionLocal = async_sessionmaker(
3635
self.engine,
3736
class_=AsyncSession,
3837
expire_on_commit=False,

astrbot/core/db/migration/migra_3_to_4.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,7 @@ async def migration_conversation_table(
7070
logger.info(
7171
f"未找到该条旧会话对应的具体数据: {conversation}, 跳过。",
7272
)
73+
continue
7374
if ":" not in conv.user_id:
7475
continue
7576
session = MessageSesion.from_str(session_str=conv.user_id)
@@ -207,6 +208,7 @@ async def migration_webchat_data(
207208
logger.info(
208209
f"未找到该条旧会话对应的具体数据: {conversation}, 跳过。",
209210
)
211+
continue
210212
if ":" in conv.user_id:
211213
continue
212214
platform_id = "webchat"

astrbot/core/db/migration/sqlite_v3.py

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -127,7 +127,7 @@ def _get_conn(self, db_path: str) -> sqlite3.Connection:
127127
conn.text_factory = str
128128
return conn
129129

130-
def _exec_sql(self, sql: str, params: tuple = None):
130+
def _exec_sql(self, sql: str, params: tuple | None = None):
131131
conn = self.conn
132132
try:
133133
c = self.conn.cursor()
@@ -224,9 +224,11 @@ def get_grouped_base_stats(self, offset_sec: int = 86400) -> Stats:
224224

225225
c.close()
226226

227-
return Stats(platform, [], [])
227+
return Stats(platform)
228228

229-
def get_conversation_by_user_id(self, user_id: str, cid: str) -> Conversation:
229+
def get_conversation_by_user_id(
230+
self, user_id: str, cid: str
231+
) -> Conversation | None:
230232
try:
231233
c = self.conn.cursor()
232234
except sqlite3.ProgrammingError:
@@ -258,7 +260,7 @@ def new_conversation(self, user_id: str, cid: str):
258260
(user_id, cid, history, updated_at, created_at),
259261
)
260262

261-
def get_conversations(self, user_id: str) -> tuple:
263+
def get_conversations(self, user_id: str) -> list[Conversation]:
262264
try:
263265
c = self.conn.cursor()
264266
except sqlite3.ProgrammingError:

astrbot/core/db/po.py

Lines changed: 16 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ class PlatformStat(SQLModel, table=True):
1212
Note: In astrbot v4, we moved `platform` table to here.
1313
"""
1414

15-
__tablename__ = "platform_stats" # type: ignore
15+
__tablename__: str = "platform_stats"
1616

1717
id: int = Field(primary_key=True, sa_column_kwargs={"autoincrement": True})
1818
timestamp: datetime = Field(nullable=False)
@@ -31,9 +31,10 @@ class PlatformStat(SQLModel, table=True):
3131

3232

3333
class ConversationV2(SQLModel, table=True):
34-
__tablename__ = "conversations" # type: ignore
34+
__tablename__: str = "conversations"
3535

36-
inner_conversation_id: int = Field(
36+
inner_conversation_id: int | None = Field(
37+
default=None,
3738
primary_key=True,
3839
sa_column_kwargs={"autoincrement": True},
3940
)
@@ -68,7 +69,7 @@ class Persona(SQLModel, table=True):
6869
It can be used to customize the behavior of LLMs.
6970
"""
7071

71-
__tablename__ = "personas" # type: ignore
72+
__tablename__: str = "personas"
7273

7374
id: int | None = Field(
7475
primary_key=True,
@@ -98,7 +99,7 @@ class Persona(SQLModel, table=True):
9899
class Preference(SQLModel, table=True):
99100
"""This class represents preferences for bots."""
100101

101-
__tablename__ = "preferences" # type: ignore
102+
__tablename__: str = "preferences"
102103

103104
id: int | None = Field(
104105
default=None,
@@ -134,7 +135,7 @@ class PlatformMessageHistory(SQLModel, table=True):
134135
or platform-specific messages.
135136
"""
136137

137-
__tablename__ = "platform_message_history" # type: ignore
138+
__tablename__: str = "platform_message_history"
138139

139140
id: int | None = Field(
140141
primary_key=True,
@@ -162,7 +163,7 @@ class PlatformSession(SQLModel, table=True):
162163
Each session can have multiple conversations (对话) associated with it.
163164
"""
164165

165-
__tablename__ = "platform_sessions" # type: ignore
166+
__tablename__: str = "platform_sessions"
166167

167168
inner_id: int | None = Field(
168169
primary_key=True,
@@ -203,7 +204,7 @@ class Attachment(SQLModel, table=True):
203204
Attachments can be images, files, or other media types.
204205
"""
205206

206-
__tablename__ = "attachments" # type: ignore
207+
__tablename__: str = "attachments"
207208

208209
inner_attachment_id: int | None = Field(
209210
primary_key=True,
@@ -261,17 +262,17 @@ class Personality(TypedDict):
261262
在 v4.0.0 版本及之后,推荐使用上面的 Persona 类。并且, mood_imitation_dialogs 字段已被废弃。
262263
"""
263264

264-
prompt: str = ""
265-
name: str = ""
266-
begin_dialogs: list[str] = []
267-
mood_imitation_dialogs: list[str] = []
265+
prompt: str
266+
name: str
267+
begin_dialogs: list[str]
268+
mood_imitation_dialogs: list[str]
268269
"""情感模拟对话预设。在 v4.0.0 版本及之后,已被废弃。"""
269-
tools: list[str] | None = None
270+
tools: list[str] | None
270271
"""工具列表。None 表示使用所有工具,空列表表示不使用任何工具"""
271272

272273
# cache
273-
_begin_dialogs_processed: list[dict] = []
274-
_mood_imitation_dialogs_processed: str = ""
274+
_begin_dialogs_processed: list[dict]
275+
_mood_imitation_dialogs_processed: str
275276

276277

277278
# ====

astrbot/core/db/sqlite.py

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
import typing as T
44
from datetime import datetime, timedelta, timezone
55

6+
from sqlalchemy import CursorResult
67
from sqlalchemy.ext.asyncio import AsyncSession
78
from sqlmodel import col, delete, desc, func, or_, select, text, update
89

@@ -489,7 +490,7 @@ async def get_attachments(self, attachment_ids: list[str]) -> list:
489490
async with self.get_db() as session:
490491
session: AsyncSession
491492
query = select(Attachment).where(
492-
Attachment.attachment_id.in_(attachment_ids)
493+
col(Attachment.attachment_id).in_(attachment_ids)
493494
)
494495
result = await session.execute(query)
495496
return list(result.scalars().all())
@@ -505,7 +506,7 @@ async def delete_attachment(self, attachment_id: str) -> bool:
505506
query = delete(Attachment).where(
506507
col(Attachment.attachment_id) == attachment_id
507508
)
508-
result = await session.execute(query)
509+
result = T.cast(CursorResult, await session.execute(query))
509510
return result.rowcount > 0
510511

511512
async def delete_attachments(self, attachment_ids: list[str]) -> int:
@@ -521,7 +522,7 @@ async def delete_attachments(self, attachment_ids: list[str]) -> int:
521522
query = delete(Attachment).where(
522523
col(Attachment.attachment_id).in_(attachment_ids)
523524
)
524-
result = await session.execute(query)
525+
result = T.cast(CursorResult, await session.execute(query))
525526
return result.rowcount
526527

527528
async def insert_persona(

0 commit comments

Comments
 (0)