乐于分享
好东西不私藏

Hermes-Agent-工具系统源码全解析-微信公众号排版

Hermes-Agent-工具系统源码全解析-微信公众号排版

Hermes Agent 工具系统源码全解析

注册表自注册、按需加载与动态 Schema 重写 [04]

导读 [04] Hermes Agent 工具系统源码全解析:589 行的注册表如何驱动 70+ 工具自注册、28 个工具集按需加载与动态 Schema 重写

[04] Hermes Agent 工具系统源码全解析:589 行的注册表如何驱动 70+ 工具自注册、28 个工具集按需加载与动态 Schema 重写

TL;DR:Hermes Agent 的工具系统不是一个大 switch-case。tools/registry.py(589行)是一个单例注册表,每个工具在模块顶层调用 registry.register() 自注册;model_tools.py 再根据启用的工具集做过滤、缓存、动态 Schema 重写。这篇从 registry.register() 到 dispatch() 的完整链路拆一遍——自注册发现、check_fn TTL 缓存、跨工具集重名保护、动态 Schema 覆盖。

---

上篇拆了 System Prompt 组装,这篇拆 Agent 的「手和脚」——工具系统。

你可能觉得工具系统没什么好讲的:不就是一堆函数挂上去吗?但 Hermes 的工具系统有 4 个值得单独写一篇文章的设计:

1. 自注册发现——70+ 个工具文件不会在代码里显式 import,而是通过 AST 扫描自动发现 2. check_fn TTL 缓存——每个工具集的可用性检查不是每次请求都跑,而是 30 秒缓存 3. 跨工具集重名保护——MCP 插件注册的工具不能覆盖内置工具(除非主动 opt-in) 4. 动态 Schema 重写——execute_codediscord 等工具的 Schema 在运行时根据配置重写

下面从注册表源码逐层拆。

---

1. 注册表内核:ToolRegistry 单例

入口文件 tools/registry.py(589 行),最尾部创建了模块级单例:

# Module-level singleton

registry = ToolRegistry()

所有工具文件都从模块顶层导入这个 registry 并调用 registry.register()。这个单例是整个工具系统的唯一真相来源——model_tools.pyrun_agent.pycli.py 都从它这里查询,没有平行数据。

ToolRegistry 的数据结构很简单——一个 Dict[str, ToolEntry]

class ToolEntry:

__slots__= (

"name","toolset", "schema", "handler", "check_fn",

"requires_env","is_async", "description", "emoji",

"max_result_size_chars","dynamic_schema_overrides",

)

关键字段:

图 1:复杂表格已转换为 PNG,降低公众号导入变形风险。

---

2. 自注册发现:不靠手动 import,靠 AST 扫描

传统做法是把所有工具模块写在一张 import 表里。Hermes 不做这个——它通过 AST 扫描来发现哪些模块是"工具"。

入口在 discover_builtin_tools()

def discover_builtin_tools(tools_dir=None) -> List[str]:

tools_path= Path(tools_dir) if tools_dir is not None else Path(__file__).resolve().parent

module_names= [

f"tools.{path.stem}"

forpath in sorted(tools_path.glob("*.py"))

ifpath.name not in {"__init__.py", "registry.py", "mcp_tool.py"}

and_module_registers_tools(path)# ← AST 扫描

]

imported= []

formod_name in module_names:

try:

importlib.import_module(mod_name)

imported.append(mod_name)

exceptException as e:

logger.warning("Couldnot import tool module %s: %s", mod_name, e)

returnimported

_module_registers_tools() 通过 Python 的 ast 模块分析源码——它会真正解析语法树,检查脚本的模块级别是否存在 registry.register(...) 调用:

def _module_registers_tools(module_path: Path) -> bool:

try:

source= module_path.read_text(encoding="utf-8")

tree= ast.parse(source, filename=str(module_path))

except(OSError, SyntaxError):

returnFalse

returnany(_is_registry_register_call(stmt) for stmt in tree.body)

为什么是 AST 而不是试 import?因为 import 失败可能导致级联崩溃——某个工具依赖的库没装,import 就抛异常。AST 扫描无副作作用。

def _is_registry_register_call(node: ast.AST) -> bool:

ifnot isinstance(node, ast.Expr) or not isinstance(node.value, ast.Call):

returnFalse

func= node.value.func

return(

isinstance(func,ast.Attribute)

andfunc.attr == "register"

andisinstance(func.value, ast.Name)

andfunc.value.id == "registry"

)

这段代码检查的是:表达式是否是 registry.register(...) 的 AST 结构(Name('registry') → Attribute('register') → Call)。

> 扫描发现后,Hermes 会自动 import 匹配的模块。import 触发模块顶层的 registry.register() 调用,工具就注册了。

---

3. register():从工具文件到注册表

每个工具文件的末尾(或模块顶层)都有一行类似这样的代码:

# 摘自 tools/browser_tool.py(示意,非真实代码)

from tools.registry import registry, tool_result

def _handle_browser_navigate(args):

...

registry.register(

name="browser_navigate",

toolset="browser",

schema={

"description":"导航到指定 URL",

"parameters":{

"type":"object",

"properties":{

"url":{"type": "string", "description": "目标 URL"}

},

"required":["url"]

}

},

handler=_handle_browser_navigate,

check_fn=_check_playwright_installed,#实际检查函数

requires_env=["PLAYWRIGHT_BROWSER_PATH"],

)

register() 的内部逻辑做了三件事:

def register(self, name, toolset, schema, handler, check_fn=None,

requires_env=None,is_async=False, description="",

emoji="",max_result_size_chars=None,

dynamic_schema_overrides=None,override=False):

withself._lock:

existing= self._tools.get(name)

ifexisting and existing.toolset != toolset:

#跨工具集重名保护

both_mcp= (

existing.toolset.startswith("mcp-")

andtoolset.startswith("mcp-")

)

ifboth_mcp:

pass#MCP 同名工具间的覆盖是合法的

elifoverride:

pass#显式 opt-in 覆盖

else:

logger.error("Toolregistration REJECTED: '%s' ...")

return#❌ 拒绝注册

#注册工具

self._tools[name]= ToolEntry(...)

ifcheck_fn and toolset not in self._toolset_checks:

self._toolset_checks[toolset]= check_fn

self._generation+= 1# ← 版本号递增,通知缓存失效

_generation 是一个单调递增的计数器。每次注册/注销/别名变更都会递增。model_tools.py 的缓存会把这个 generation 作为 cache key 的一部分——generation 不变说明注册表状态没变,可以直接返回缓存。

跨工具集重名保护的场景

场景

行为

内置工具(toolset="terminal")+ MCP 插件注册同名

❌ 拒绝,除非 MCP 服务的工具覆盖

两个 MCP 服务注册同名

✅ 允许(后注册覆盖先注册)

插件 `override=True`

✅ 允许(插件作者明确 opt-in)

---

4. check_fn TTL 缓存:30 秒弹性

check_fn 是工具集可用性检测函数。例如 terminal 工具集的 check_fn 探测 Docker daemon、Modal SDK 是否存在;browser 工具集的 check_fn 探测 playwright 是否安装。

如果每次获取工具定义都重新跑一遍这些检测,启动时还好,但在一个长驻进程里(Gateway)就浪费了。Hermes 用了 30 秒 TTL 缓存:

_CHECK_FN_TTL_SECONDS = 30.0

_check_fn_cache: Dict[Callable, tuple[float, bool]] = {}

def _check_fn_cached(fn: Callable) -> bool:

now= time.monotonic()

with_check_fn_cache_lock:

cached= _check_fn_cache.get(fn)

ifcached is not None:

ts,value = cached

ifnow - ts < _CHECK_FN_TTL_SECONDS:

returnvalue# ← 命中缓存

try:

value= bool(fn())

exceptException:

value= False

with_check_fn_cache_lock:

_check_fn_cache[fn]= (now, value)

returnvalue

为什么 30 秒?注释里写了理由:

> 30s TTL chosen so env-var changes (hermes tools enable foo) still take effect in near-real-time without forcing a full cache flush on every call.

太短(如 5 秒)→ 每次 get_definitions() 都重新探测,浪费。太长(如 300 秒)→ 用户 hermes tools enable browser 后要等 5 分钟才能生效。30 秒是实测后的折中值。

同时还有一个单次调用的内存缓存(check_results: Dict[Callable, bool] = {})——在单次 get_definitions() 调用内,同一个 check_fn 不会被重复执行。

---

5. get_definitions():从注册表到模型的工具 JSON

model_tools.py 中的 get_tool_definitions() 是连接注册表和 Agent Loop 的桥梁。它的核心流程:

5.1 传入工具集列表,解析出工具名

def _compute_tool_definitions(enabled_toolsets, disabled_toolsets, ...):

tools_to_include= set()

ifenabled_toolsets is not None:

fortoolset_name in effective_enabled_toolsets:

ifvalidate_toolset(toolset_name):

resolved= resolve_toolset(toolset_name)

tools_to_include.update(resolved)

else:

#默认:加载所有工具集

forts_name in get_all_toolsets():

tools_to_include.update(resolve_toolset(ts_name))

#禁用工具集作为减法

ifdisabled_toolsets:

fortoolset_name in disabled_toolsets:

resolved= resolve_toolset(toolset_name)

tools_to_include.difference_update(resolved)

注意 kanban worker 的特殊处理:

if os.environ.get("HERMES_KANBAN_TASK") and "kanban" not in effective_enabled_toolsets:

effective_enabled_toolsets.append("kanban")

Dispatcher 启动了 kanban worker,即使 Profile 配置中没有 kanban 工具集,Worker 也必须有 kanban 工具集——否则 Worker 无法上报进度、无法完成/阻塞任务。这是强制注入,不受 Profile 配置影响。

5.2 动态 Schema 重写

工具注册时的 Schema 是静态的,但某些工具的 Schema 必须在运行时根据配置动态调整。

execute_code 是典型例子。它的 Schema 中有一个 sandbox_allowed_tools 数组,列出在 execute_code 沙箱中可用的工具。但这个列表必须实时反映实际启用的工具——如果 web_search 工具集被禁用了,沙箱中也必须不可见:

if "execute_code" in available_tool_names:

fromtools.code_execution_tool import SANDBOX_ALLOWED_TOOLS, build_execute_code_schema

sandbox_enabled= SANDBOX_ALLOWED_TOOLS & available_tool_names

dynamic_schema= build_execute_code_schema(sandbox_enabled, mode=_get_execution_mode())

fori, td in enumerate(filtered_tools):

iftd.get("function", {}).get("name") == "execute_code":

filtered_tools[i]= {"type": "function", "function": dynamic_schema}

break

discord 和 discord_admin 也有类似的动态重写——基于 Discord Bot 的实际 intents(从 GET /applications/@me 检测)隐藏不支持的操作:

_discord_schema_fns = {

"discord":"get_dynamic_schema_core",

"discord_admin":"get_dynamic_schema_admin",

}

for discord_tool_name in _discord_schema_fns:

ifdiscord_tool_name in available_tool_names:

fromtools import discord_tool as _dt

schema_fn= getattr(_dt, _discord_schema_fns[discord_tool_name])

dynamic= schema_fn()

ifdynamic:

#替换静态 Schema

除了这些硬编码的动态重写,Registry 还支持通用的 dynamic_schema_overrides 回调:

if entry.dynamic_schema_overrides is not None:

try:

overrides= entry.dynamic_schema_overrides()

ifisinstance(overrides, dict):

schema_with_name.update(overrides)

exceptException as exc:

logger.warning("dynamic_schema_overridesfor tool %s raised %s", name, exc)

这个回调在 get_definitions() 每次调用时执行,返回的 dict 会和静态 Schema 做浅合并delegate_task 就利用这个机制——它的 max_concurrent_children 和 max_spawn_depth 参数描述必须反映当前配置值:

# tools/delegate_task.py(示意)

registry.register(

name="delegate_task",

toolset="agent",

dynamic_schema_overrides=_current_delegation_config,#运行时回调

...

)

5.3 缓存策略

整个 get_tool_definitions() 支持多层缓存:

# 最外层:model_tools 的内存缓存(以 registry generation + 配置 mtime 为 key)

if quiet_mode:

cache_key= (

frozenset(enabled_toolsets),

frozenset(disabled_toolsets),

registry._generation,#注册表版本

(cfg_path.stat().st_mtime_ns,cfg_path.stat().st_size),# 配置文件指纹

bool(os.environ.get("HERMES_KANBAN_TASK")),

)

cached= _tool_defs_cache.get(cache_key)

ifcached is not None:

returnlist(cached)

# 次外层:registry.get_definitions() 内部的 check_fn TTL 缓存

filtered_tools = registry.get_definitions(tools_to_include, quiet=quiet_mode)

两个缓存层级互不覆盖——外层按配置+版本缓存整个结果列表,内层只缓存 check_fn 的执行结果。

---

6. dispatch():从模型调用到工具执行

当模型返回 tool_calls 时,Agent Loop 调用 registry.dispatch()

def dispatch(self, name: str, args: dict) -> str:

entry= self.get_entry(name)

ifnot entry:

returnjson.dumps({"error": f"Unknown tool: {name}"})

try:

ifentry.is_async:

frommodel_tools import _run_async

return_run_async(entry.handler(args))

returnentry.handler(args)

exceptException as e:

logger.exception("Tool%s dispatch error: %s", name, e)

raw= f"Tool execution failed: {type(e).__name__}: {e}"

try:

frommodel_tools import _sanitize_tool_error

sanitized= _sanitize_tool_error(raw)

exceptException:

sanitized= raw

returnjson.dumps({"error": sanitized})

异常处理的细节:错误信息通过 _sanitize_tool_error() 过滤——防止 framing token、CDATA、反引号等结构性噪音污染模型的下一次推理。

每个工具的处理函数必须返回 JSON 字符串。注册表提供了两个通用辅助函数:

def tool_error(message, **extra) -> str:

result= {"error": str(message)}

ifextra:

result.update(extra)

returnjson.dumps(result, ensure_ascii=False)

def tool_result(data=None, **kwargs) -> str:

ifdata is not None:

returnjson.dumps(data, ensure_ascii=False)

returnjson.dumps(kwargs, ensure_ascii=False)

使用方式:

return tool_result(success=True, count=42)

# → '{"success": true, "count": 42}'

return tool_error("file not found", code=404)

# → '{"error": "file not found", "code": 404}'

---

7. 工具集模型:从注册到解析的完整链路

把整条链路串起来:

工具文件(tools/*.py)# 每个工具独立文件

模块顶层 registry.register()

ToolRegistry(tools/registry.py)# 单例注册表

get_definitions() → 按 check_fn 过滤 → 缓存

model_tools.get_tool_definitions()# 工具集解析 + 动态 Schema 重写

Agent Loop 获取 → 注入 API 请求

LLM 返回 tool_calls

Agent Loop → registry.dispatch(name, args)# 执行工具

异常 → _sanitize_tool_error() → 返回 JSON

工具结果回填对话历史,进入下一轮迭代

---

8. 这篇文章的代码索引

图 2:复杂表格已转换为 PNG,降低公众号导入变形风险。

已注册的工具命名来源:每个工具文件就是一个工具,文件名即工具名(在 registry.register() 的 name 参数中指定)。

---

下一篇拆记忆矩阵——MEMORY.md、Hindsight 向量库、state.db SQLite 三层架构的协同与冲突。

---

*本系列基于 Hermes Agent v0.15.2 源码。工具系统文件:tools/registry.py(589 行)+ model_tools.py(1174 行)。*

基本 文件 流程 错误 SQL 调试
  1. 请求信息 : 2026-06-20 17:44:00 HTTP/1.1 GET : https://www.yeyulingfeng.com/a/774778.html
  2. 运行时间 : 0.093785s [ 吞吐率:10.66req/s ] 内存消耗:4,926.01kb 文件加载:145
  3. 缓存信息 : 0 reads,0 writes
  4. 会话信息 : SESSION_ID=7badceb8a848b29a81ae734f8725eed1
  1. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/public/index.php ( 0.79 KB )
  2. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/autoload.php ( 0.17 KB )
  3. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/composer/autoload_real.php ( 2.49 KB )
  4. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/composer/platform_check.php ( 0.90 KB )
  5. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/composer/ClassLoader.php ( 14.03 KB )
  6. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/composer/autoload_static.php ( 6.05 KB )
  7. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-helper/src/helper.php ( 8.34 KB )
  8. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-validate/src/helper.php ( 2.19 KB )
  9. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/ralouphie/getallheaders/src/getallheaders.php ( 1.60 KB )
  10. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/helper.php ( 1.47 KB )
  11. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/stubs/load_stubs.php ( 0.16 KB )
  12. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Exception.php ( 1.69 KB )
  13. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-container/src/Facade.php ( 2.71 KB )
  14. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/symfony/deprecation-contracts/function.php ( 0.99 KB )
  15. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/symfony/polyfill-mbstring/bootstrap.php ( 8.26 KB )
  16. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/symfony/polyfill-mbstring/bootstrap80.php ( 9.78 KB )
  17. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/symfony/var-dumper/Resources/functions/dump.php ( 1.49 KB )
  18. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-dumper/src/helper.php ( 0.18 KB )
  19. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/symfony/var-dumper/VarDumper.php ( 4.30 KB )
  20. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/guzzlehttp/guzzle/src/functions_include.php ( 0.16 KB )
  21. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/guzzlehttp/guzzle/src/functions.php ( 5.54 KB )
  22. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/App.php ( 15.30 KB )
  23. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-container/src/Container.php ( 15.76 KB )
  24. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/psr/container/src/ContainerInterface.php ( 1.02 KB )
  25. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/app/provider.php ( 0.19 KB )
  26. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Http.php ( 6.04 KB )
  27. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-helper/src/helper/Str.php ( 7.29 KB )
  28. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Env.php ( 4.68 KB )
  29. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/app/common.php ( 0.03 KB )
  30. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/helper.php ( 18.78 KB )
  31. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Config.php ( 5.54 KB )
  32. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/alipay.php ( 3.59 KB )
  33. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/facade/Env.php ( 1.67 KB )
  34. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/app.php ( 0.95 KB )
  35. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/cache.php ( 0.78 KB )
  36. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/console.php ( 0.23 KB )
  37. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/cookie.php ( 0.56 KB )
  38. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/database.php ( 2.48 KB )
  39. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/filesystem.php ( 0.61 KB )
  40. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/lang.php ( 0.91 KB )
  41. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/log.php ( 1.35 KB )
  42. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/middleware.php ( 0.19 KB )
  43. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/route.php ( 1.89 KB )
  44. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/session.php ( 0.57 KB )
  45. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/trace.php ( 0.34 KB )
  46. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/config/view.php ( 0.82 KB )
  47. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/app/event.php ( 0.25 KB )
  48. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Event.php ( 7.67 KB )
  49. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/app/service.php ( 0.13 KB )
  50. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/app/AppService.php ( 0.26 KB )
  51. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Service.php ( 1.64 KB )
  52. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Lang.php ( 7.35 KB )
  53. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/lang/zh-cn.php ( 13.70 KB )
  54. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/initializer/Error.php ( 3.31 KB )
  55. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/initializer/RegisterService.php ( 1.33 KB )
  56. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/services.php ( 0.14 KB )
  57. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/service/PaginatorService.php ( 1.52 KB )
  58. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/service/ValidateService.php ( 0.99 KB )
  59. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/service/ModelService.php ( 2.04 KB )
  60. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-trace/src/Service.php ( 0.77 KB )
  61. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Middleware.php ( 6.72 KB )
  62. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/initializer/BootService.php ( 0.77 KB )
  63. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/Paginator.php ( 11.86 KB )
  64. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-validate/src/Validate.php ( 63.20 KB )
  65. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/Model.php ( 23.55 KB )
  66. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/model/concern/Attribute.php ( 21.05 KB )
  67. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/model/concern/AutoWriteData.php ( 4.21 KB )
  68. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/model/concern/Conversion.php ( 6.44 KB )
  69. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/model/concern/DbConnect.php ( 5.16 KB )
  70. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/model/concern/ModelEvent.php ( 2.33 KB )
  71. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/model/concern/RelationShip.php ( 28.29 KB )
  72. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-helper/src/contract/Arrayable.php ( 0.09 KB )
  73. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-helper/src/contract/Jsonable.php ( 0.13 KB )
  74. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/model/contract/Modelable.php ( 0.09 KB )
  75. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Db.php ( 2.88 KB )
  76. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/DbManager.php ( 8.52 KB )
  77. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Log.php ( 6.28 KB )
  78. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Manager.php ( 3.92 KB )
  79. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/psr/log/src/LoggerTrait.php ( 2.69 KB )
  80. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/psr/log/src/LoggerInterface.php ( 2.71 KB )
  81. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Cache.php ( 4.92 KB )
  82. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/psr/simple-cache/src/CacheInterface.php ( 4.71 KB )
  83. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-helper/src/helper/Arr.php ( 16.63 KB )
  84. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/cache/driver/File.php ( 7.84 KB )
  85. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/cache/Driver.php ( 9.03 KB )
  86. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/contract/CacheHandlerInterface.php ( 1.99 KB )
  87. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/app/Request.php ( 0.09 KB )
  88. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Request.php ( 55.78 KB )
  89. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/app/middleware.php ( 0.25 KB )
  90. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Pipeline.php ( 2.61 KB )
  91. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-trace/src/TraceDebug.php ( 3.40 KB )
  92. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/middleware/SessionInit.php ( 1.94 KB )
  93. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Session.php ( 1.80 KB )
  94. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/session/driver/File.php ( 6.27 KB )
  95. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/contract/SessionHandlerInterface.php ( 0.87 KB )
  96. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/session/Store.php ( 7.12 KB )
  97. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Route.php ( 23.73 KB )
  98. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/route/RuleName.php ( 5.75 KB )
  99. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/route/Domain.php ( 2.53 KB )
  100. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/route/RuleGroup.php ( 22.43 KB )
  101. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/route/Rule.php ( 26.95 KB )
  102. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/route/RuleItem.php ( 9.78 KB )
  103. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/route/app.php ( 3.94 KB )
  104. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/facade/Route.php ( 4.70 KB )
  105. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/route/dispatch/Controller.php ( 4.74 KB )
  106. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/route/Dispatch.php ( 10.44 KB )
  107. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/app/controller/Index.php ( 9.87 KB )
  108. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/app/BaseController.php ( 2.05 KB )
  109. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/facade/Db.php ( 0.93 KB )
  110. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/connector/Mysql.php ( 5.44 KB )
  111. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/PDOConnection.php ( 52.47 KB )
  112. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/Connection.php ( 8.39 KB )
  113. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/ConnectionInterface.php ( 4.57 KB )
  114. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/builder/Mysql.php ( 16.58 KB )
  115. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/Builder.php ( 24.06 KB )
  116. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/BaseBuilder.php ( 27.50 KB )
  117. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/Query.php ( 15.71 KB )
  118. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/BaseQuery.php ( 45.13 KB )
  119. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/concern/TimeFieldQuery.php ( 7.43 KB )
  120. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/concern/AggregateQuery.php ( 3.26 KB )
  121. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/concern/ModelRelationQuery.php ( 20.07 KB )
  122. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/concern/ParamsBind.php ( 3.66 KB )
  123. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/concern/ResultOperation.php ( 7.01 KB )
  124. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/concern/WhereQuery.php ( 19.37 KB )
  125. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/concern/JoinAndViewQuery.php ( 7.11 KB )
  126. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/concern/TableFieldInfo.php ( 2.63 KB )
  127. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-orm/src/db/concern/Transaction.php ( 2.77 KB )
  128. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/log/driver/File.php ( 5.96 KB )
  129. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/contract/LogHandlerInterface.php ( 0.86 KB )
  130. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/log/Channel.php ( 3.89 KB )
  131. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/event/LogRecord.php ( 1.02 KB )
  132. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-helper/src/Collection.php ( 16.47 KB )
  133. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/facade/View.php ( 1.70 KB )
  134. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/View.php ( 4.39 KB )
  135. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/app/controller/Es.php ( 3.30 KB )
  136. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Response.php ( 8.81 KB )
  137. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/response/View.php ( 3.29 KB )
  138. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/Cookie.php ( 6.06 KB )
  139. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-view/src/Think.php ( 8.38 KB )
  140. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/framework/src/think/contract/TemplateHandlerInterface.php ( 1.60 KB )
  141. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-template/src/Template.php ( 46.61 KB )
  142. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-template/src/template/driver/File.php ( 2.41 KB )
  143. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-template/src/template/contract/DriverInterface.php ( 0.86 KB )
  144. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/runtime/temp/c935550e3e8a3a4c27dd94e439343fdf.php ( 31.50 KB )
  145. /yingpanguazai/ssd/ssd1/www/wwww.yeyulingfeng.com/vendor/topthink/think-trace/src/Html.php ( 4.42 KB )
  1. CONNECT:[ UseTime:0.000698s ] mysql:host=127.0.0.1;port=3306;dbname=wenku;charset=utf8mb4
  2. SHOW FULL COLUMNS FROM `fenlei` [ RunTime:0.000786s ]
  3. SELECT * FROM `fenlei` WHERE `fid` = 0 [ RunTime:0.000330s ]
  4. SELECT * FROM `fenlei` WHERE `fid` = 63 [ RunTime:0.000292s ]
  5. SHOW FULL COLUMNS FROM `set` [ RunTime:0.000521s ]
  6. SELECT * FROM `set` [ RunTime:0.000211s ]
  7. SHOW FULL COLUMNS FROM `article` [ RunTime:0.000524s ]
  8. SELECT * FROM `article` WHERE `id` = 774778 LIMIT 1 [ RunTime:0.000457s ]
  9. UPDATE `article` SET `lasttime` = 1781948640 WHERE `id` = 774778 [ RunTime:0.001954s ]
  10. SELECT * FROM `fenlei` WHERE `id` = 64 LIMIT 1 [ RunTime:0.000258s ]
  11. SELECT * FROM `article` WHERE `id` < 774778 ORDER BY `id` DESC LIMIT 1 [ RunTime:0.000437s ]
  12. SELECT * FROM `article` WHERE `id` > 774778 ORDER BY `id` ASC LIMIT 1 [ RunTime:0.000362s ]
  13. SELECT * FROM `article` WHERE `id` < 774778 ORDER BY `id` DESC LIMIT 10 [ RunTime:0.000618s ]
  14. SELECT * FROM `article` WHERE `id` < 774778 ORDER BY `id` DESC LIMIT 10,10 [ RunTime:0.000805s ]
  15. SELECT * FROM `article` WHERE `id` < 774778 ORDER BY `id` DESC LIMIT 20,10 [ RunTime:0.001179s ]
0.095464s