mcpField
C
clojure-eval

clojure-eval

github.com/bhauman开发196155 次安装19 周前更新
代码仓库

关于 clojure-eval

clojure-eval 是通过 nREPL 服务执行 Clojure 代码的技能,适用于需要测试函数、检查会话或确认命名空间可加载的开发者。它支持发现端口并在多次求值间保留会话状态。

主要功能

  1. 01发现 nREPL 服务
  2. 02求值 Clojure 表达式
  3. 03在求值间保留状态
  4. 04重新加载命名空间以测试
  5. 05重置会话并设置超时

适用场景

  1. 01检查修改后的命名空间能否编译
  2. 02交互式试运行函数调用
  3. 03查看运行中及已连接的 nREPL 会话

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/bhauman/clojure-mcp-light --skill clojure-eval

安装后在 Claude Code 中输入/clojure-eval确认已加载。

附带文件examples.md

详细介绍

Clojure REPL 求值

何时使用此技能

在以下情况下使用此技能:

  • 验证编辑后的 Clojure 文件能否正确编译和加载
  • 交互式测试函数行为
  • 检查 REPL 的当前状态
  • 通过求值表达式调试代码
  • 为测试引入或加载命名空间
  • 在提交前验证代码更改是否有效

工作原理

clj-nrepl-eval 命令会针对 nREPL 服务求值 Clojure 代码。会话状态会在各次求值之间保留,因此你可以在一次求值中引入命名空间,并在后续调用中使用它。每个 host:port 组合都有自己的会话文件。

说明

0. 发现并选择 nREPL 服务

首先,发现当前目录中正在运行的 nREPL 服务:

clj-nrepl-eval --discover-ports

这会显示当前项目目录中正在运行的所有 nREPL 服务(Clojure、Babashka、shadow-cljs 等)。

然后使用 AskUserQuestion 工具:

  • 如果发现了端口: 提示用户选择要使用的 nREPL 端口:

    • question:“要使用哪个 nREPL 端口?”
    • header:“nREPL 端口”
    • options: 将每个发现的端口作为一个选项列出,其中包含:
      • label: 端口号
      • description: 服务类型和状态(例如,“当前目录中的 Clojure nREPL 服务”)
    • 最多列出 4 个发现的端口作为选项
    • 用户可以选择“Other”来输入自定义端口号
  • 如果未发现端口: 提示用户如何启动 nREPL 服务:

    • question:“未找到 nREPL 服务。要如何启动一个?”
    • header:“启动 nREPL”
    • options:
      • label:“deps.edn 别名”,description:“在 deps.edn 中查找并使用 nREPL 别名”
      • label:“Leiningen”,description:“使用 'lein repl' 启动 nREPL”
    • 用户可以选择“Other”以使用其他方法,或在特定端口上已有服务运行时选择该项

重要:如果启动 REPL,不要指定端口;让 nREPL 启动并返回其使用的端口。

1. 求值 Clojure 代码

求值时会自动连接到指定端口

使用 -p 标志指定端口,并传入 Clojure 代码。

建议:通过 stdin 使用 heredoc,以避免 shell 转义问题。单引号分隔符(<<'EOF')会原样传递所有字符。

clj-nrepl-eval -p <PORT> <<'EOF'
(+ 1 2 3)
EOF

多个表达式:

clj-nrepl-eval -p <PORT> <<'EOF'
(def x 10)
(+ x 20)
EOF
2. 显示 nREPL 会话

发现当前目录中的所有 nREPL 服务:

clj-nrepl-eval --discover-ports

显示当前项目目录中正在运行的所有 nREPL 服务,包括其类型(clj/bb/basilisp)以及它们是否与当前工作目录匹配。

检查之前连接过的会话:

clj-nrepl-eval --connected-ports

仅显示你之前建立的连接(在首次通过某个端口求值后显示)。

3. 常见用法

引入命名空间(始终使用 :reload 以获取更改):

clj-nrepl-eval -p <PORT> "(require '[my.namespace :as ns] :reload)"

引入命名空间后测试函数:

clj-nrepl-eval -p <PORT> "(ns/my-function arg1 arg2)"

检查文件是否能编译:

clj-nrepl-eval -p <PORT> "(require 'my.namespace :reload)"

多个表达式:

clj-nrepl-eval -p <PORT> "(def x 10) (* x 2) (+ x 5)"

复杂的多行代码:

clj-nrepl-eval -p <PORT> <<'EOF'
(def x 10)
(* x 2)
(+ x 5)
EOF

自定义超时时间(毫秒):

clj-nrepl-eval -p <PORT> --timeout 5000 "(long-running-fn)"

重置会话(清除所有状态):

clj-nrepl-eval -p <PORT> --reset-session
clj-nrepl-eval -p <PORT> --reset-session "(def x 1)"

可用选项

  • -p, --port PORT - nREPL 端口(必填)
  • -H, --host HOST - nREPL 主机(默认值:127.0.0.1)
  • -t, --timeout MILLISECONDS - 超时时间(默认值:120000 = 2 分钟)
  • -r, --reset-session - 重置持久化的 nREPL 会话
  • -c, --connected-ports - 列出之前连接过的 nREPL 会话
  • -d, --discover-ports - 发现当前目录中的 nREPL 服务
  • -h, --help - 显示帮助信息

重要提示

  • 优先通过标准输入使用 heredoc: 使用 clj-nrepl-eval -p <PORT> <<'EOF' ... EOF,避免 shell 转义问题
  • 会话会持续保留: 状态(变量、命名空间、已加载的库)会在多次调用之间持续保留,直到 nREPL 服务器重启。--reset-session 只会重置 nREPL 会话(清除 *e、*1 等动态变量),不会清除通过 def 定义的变量或已加载的命名空间
  • 自动修复分隔符: 工具会自动修复缺失或不匹配的括号
  • 始终使用 :reload: 引入命名空间时,使用 :reload 以获取最新更改
  • 默认超时: 2 分钟(120000ms)——长时间运行的操作请增大超时时间
  • 输入优先级: 命令行参数优先于标准输入

典型工作流

  1. 发现 nREPL 服务器:clj-nrepl-eval --discover-ports
  2. 使用 AskUserQuestion 工具提示用户选择端口
  3. 引入命名空间:
    clj-nrepl-eval -p <PORT> "(require '[my.ns :as ns] :reload)"
    
  4. 测试函数:
    clj-nrepl-eval -p <PORT> "(ns/my-fn ...)"
    
  5. 迭代:进行更改,使用 :reload 重新引入,再次测试

评论

支持 Markdown