Spherewright开发日志

0x01 从落地到红糖,再到出发搬钛之前

从新档落地写到第一条红糖线,再补齐动力引擎、供电和移动保护。记录 Agent 在母星上踩过的坑,停在首次跨星球搬钛之前。


上一篇介绍了 Spherewright 的起点和接入方式。这篇回头补上实际开局的过程:从伊卡洛斯落地开始,让母星上的基础工厂转起来,做出红糖(能量矩阵),再准备去其他星球搬钛。

能对应到实际日期的记录主要在 8 月 31 日至 9 月 1 日首次起飞前;更早的落地时刻没有保留精确现实时间。文中的产线进度都属于这条长期开发主线。

对玩过《戴森球计划》的人来说,这段流程应该很熟悉。采矿、冶炼、做蓝糖(电磁矩阵),接着找油、炼石墨、做红糖,研究能飞出母星的升级。轮到 Agent 来做,麻烦经常出在一只分拣器、一根电线杆,或者伊卡洛斯脚下的建筑基座上。

这时的工具也是边玩边补:游戏暴露一个问题,就查调用、改代码、验证,再接着往下走。

下面也把这些改动记在对应的现场里。工具名统一省略 spherewright_ 前缀,比如 prepare_build 的完整名字是 spherewright_prepare_build。有些问题需要新增入口,有些只改了已有工具的校验或返回数据,还有一些靠调整产线就能解决。

开局先接出哪些基本工具

最早的桥接版本先接出了 34 个基础工具。其中 14 个负责观察,让 Agent 能知道当前处境、可用配方和动作结果。

只读工具要解决的问题
get_statusget_session_state确认 Bridge 是否可用、当前处于哪个会话和星球,以及存档归属、写入状态和阻止操作的原因。
get_player_state读取伊卡洛斯的位置、移动、能量、背包和燃料,给接近目标与材料预算提供依据。
get_progression_state查看科技、升级、解锁和科研队列,判断下一步能做什么。
get_recipe_catalogget_build_catalog读取配方、原料产物和建筑目录,避免 Agent 凭记忆猜物品编号或成本。
list_resource_nodesinspect_resource_node先分页找矿脉、植被等资源,再复读一个具体节点的类型、位置、剩余量和距离。
list_factory_entitiesinspect_factory_entity找到建筑或预建筑,再查看精确实体的组件、配方、缓冲、连接和供电。
list_assemblersinspect_assembler保留专门的制造设备查询入口,查看设备的配方和生产状态。
get_power_summary看电网连接和供需,区分没接网、没电源与运行负载过高。
get_action_result根据已接受动作的 ID 查询执行进度和终态,判断是否真的完成。

另外 20 个按十组准备/提交配对。准备阶段给出预算、前提条件和计划,不改动游戏;提交阶段重新复核,通过后才执行那一步正常游戏操作。

操作工具做什么,以及为什么单独保留这一步
prepare_new_game / commit_new_game按约定设置新建并登记 owned 世界,让后续操作有明确的存档归属。
prepare_move / commit_move下达原生移动订单,让机甲实际走到目标附近,距离和能量仍然有意义。
prepare_harvest / commit_harvest对一个确切资源节点正常手采,核对资源减少和背包增加。
prepare_handcraft / commit_handcraft把配方送进原生手搓队列,正常消耗原料并等待制作。
prepare_select_research / commit_select_research选择或排队科技,科研进度由游戏中的材料消耗继续推进。
prepare_build / commit_build检查建筑库存和合法落点,再创建预建筑,等待建设无人机完工。
prepare_configure_building / commit_configure_building为满足条件的设备设置配方、研究模式或过滤,把“建好”和“设成能工作”分开确认。
prepare_transfer / commit_transfer在玩家和受支持的存储之间搬指定数量的物品,核对两端变化。
prepare_refuel / commit_refuel把真实燃料按正常机制补入机甲燃料仓,能量仍由燃烧产生。
prepare_save / commit_save正常保存当前 owned 世界,把验证过的产线进度留在同一局里。

这些工具组成了最初的操作范围。调用顺序由 Agent 自己安排,每个动作仍有独立的材料预算、受理记录和最终结果。提交一旦被受理,就要查同一个动作的结果,或重新读取两端状态来核对,不能换个幂等键再执行一次——后面分拣器一节就有一次实际样本。

至于恢复、隔离核销和 Journal 这几样,则是开局之后处理具体问题时才陆续接上的,下面会在各自的现场提到。

先把基础材料交给机器

最开始还是要靠手采和手搓。先拿到启动材料,做出矿机、熔炉、传送带和分拣器,再一点点接出铁、铜、磁铁、磁线圈和电路板,供给蓝糖,也供给后续要用的建筑。

实际串起来,就是先查矿点和配方,手采、手搓备料,再施工和配置设备。材料不足、配方没解锁、端口不合法时,能从对应的准备结果知道卡在哪一步。

这里给自己定的要求是,手搓可以补启动资源,产线里程碑必须由机器完成。背包里有蓝糖还不够,要能读到生产设备的输入、工作状态和输出变化。建造也是一样:背包扣掉一台机器之后,还得等建设无人机把预建筑完成,才能继续接线。

做到这里,Agent 已经能把几种工具串起来用了。不过,每次扩线都还要重新确认材料、落点和端口,没到给一句“把蓝糖扩产一下”就能放心离开的程度。

接下来先把目标定在第一条自动红糖线上。红糖需要高能石墨和氢,一边从煤加工,另一边从原油精炼取得。两条线都能持续送到研究站,这个小目标才算完成。

炼油厂不动,先查那只分拣器

油井到精炼厂的第一步就碰到了接口差异。油井可以直接接出传送带,精炼厂的原油入口却需要分拣器。最初把两栋建筑都当成可以直接绑定的传送带端口,准备阶段就被拒绝了,材料没有消耗。

查清楚之后,实际搭出来的是这条路径:

油井 → 传送带 → 分拣器 → 精炼厂

线接好了,精炼厂还是不动。

先查到的是电网没有连起来。两根电线杆在那个落点相距约 22.57 米,精炼厂虽然在其中一根的覆盖范围内,所在的小电网却没有电源。补了一根中继电线杆,精炼厂终于读到了满供电。

但原油仍然进不去。继续往前查,才发现精炼厂另一侧的输入分拣器没被覆盖到。机器有电,这只分拣器依然没电。补上它附近的电塔后,状态终于发生了连续变化:分拣器拿起原油,精炼配方开始推进,原本空着的精炼油仓增加到了 15 个。

这次之后,检查供电就得细到每个消费者。只问“精炼厂有没有电”,会把最关键的入口漏掉。

这里用的仍是已有的 get_power_summaryinspect_factory_entity:前者看电网供需,后者分别读精炼厂、分拣器所在的网络和实际供电。修复发生在现场接电和 Agent 的检查顺序上;一台机器的满供电读数,不能替旁边的分拣器作证。

火电也出了一个很直白的循环:发电站等燃料,送燃料的分拣器等电。仓里明明有 18 个高能石墨,连续观察十秒,燃料就是送不进去。最后靠电线杆把已有风电接过来,分拣器先启动,火电才跟着启动。

等精炼链真的跑起来,又出现了容量问题。先前机器空闲时看着很充裕,开工后供电比例却掉到约 76%。后来把精炼油经正常物流送进新增的火电站,才恢复到满供电。开机前读到的余量,不能直接拿来当整条线运行后的余量。

分拣器建好了,也可能认错了

精炼厂有两种产物,输出要分开安排。这里还撞到了一个 Plugin 的问题:新建的分拣器和旧分拣器可以位于同一个源端位置,仅凭位置找“刚建好的那只”,会把旧实体认成新实体。

游戏里的施工已经发生,工具却无法正确确认结果。这时继续发建造指令,只会让现场更难解释。

修复放在施工前后的实体核对上。建造前先记下已有分拣器的 ID,完工后排除这些旧实体,再检查新分拣器到底从哪里取、往哪里放。同位置双输出的实机复读通过之后,才继续接下游。

对应到代码上,改的是 commit_build 背后的完工归属逻辑。prepare_build 绑定源端和目标端时,也改用专门描述端点身份、姿态和连接的 endpointStateHash。机器正常生产会改变进度和库存,若把整份设备状态都作为接线前提,读完到施工之间就可能不断报状态过期;物理端点没变时,这些生产变化不该阻止接线。

这批还新增了 prepare_quarantine_reconciliation / commit_quarantine_reconciliation,处理施工已经发生、结果却没能证明而进入写入隔离的情况。它只复查那一个未决动作,重新核对材料消耗、新实体和连接,证据完整才解除隔离。这样可以保住已经完成的施工,也避免 Agent 因为收到一次错误就再盖一遍。

随后还有一次相反的误判:公开的连接列表里少了一条关系,看着像断线,但那只分拣器实际还在取货、送货,下游仓库也继续增长。于是又撤回了这个判断,把取放目标、携货变化和库存变化一起纳入检查。

这次修正的是对 inspect_factory_entity 返回值的解释:connections 列表缺边,不足以断言当前物料流已经中断,还要交叉读取取放对象和货物变化。这些读数只能证明当时仍在搬货,持久连接是否完整还需要单独核对。

接口返回的结构化数据也要验证。少读一个字段、认错一个实体,都可能让 Agent 对着一条仍在搬货的线反复“修理”。

9 月 6 日补记:后来复核确认,这种“缺边却仍在搬货”靠的是分拣器缓存的取放目标,不能反推持久连接完整。当时的观察只证明那一刻物料流还在。新施工、升级或保存恢复之后,两端连接都要单独核对;这是后续复验收窄的经验,不代表早期版本已经验证了这些情况。详见复验记录 EXP-028、EXP-193

8 月 31 日还遇到过客户端报错,游戏其实已经完成动作:新油井已经建好,只是显示结果的代码读错了字段。对已经接受的动作,换一个幂等键重试可能再做一次。于是先查原动作结果和现场;结果无法确认时停止后续写入,不能把显示失败当成重做的理由。

第一条红糖线终于跑起来了

原油、精炼、氢的分流和石墨准备好之后,才轮到最后的研究站。

先把研究站设为能量矩阵配方,确认石墨、氢和红糖的缓冲都是零,再接入两路正常物流。之后的读取结果很简单:红糖输出从 0 → 3 → 6,随后继续积累到 10。

第一次看到这个数字连续增长,前面那些补电、接线和查端口的工作才有了一个明确的落点。材料真的经过了上游设备,最后变成了红糖。

施工期间也有一个小插曲:在正在运氢的传送带末端续接时,端点货物会正常回收到玩家身上,两次续接一共让背包多了 2 个氢。这两份单独记账,没有拿去补研究站,也没有混进自动产出的证明里。

接着补输出仓和出料分拣器,让研究站能在自身缓存满了以后继续生产。后来仓里读到 22 个红糖,其中包含之前缓存的 10 个;新增产量要扣掉这部分。再结合研究站重新工作、原料继续消耗,才确认连续出料成立。

这时红糖区的电网又被实际负载压到大约九成供电。补上一台真正接入同网的风机后,研究站和输入、输出分拣器同时工作时,供电比例恢复到了 100%。最后正常保存这一个存档,把产线和工程经验一起记成里程碑。

到这个截面,红糖已经能自动生产并进入输出仓。通往科研区的长距离自动供料线,是后面的进度,这里还没有接上。

做动力引擎,先修回老产线

红糖之后开始准备机甲升级和动力引擎。新目标很快又把问题带回了最早的铁矿区。

旧矿机覆盖的矿脉耗尽了,下游熔炉和传送带还在,原料却不再进来。处理办法是在附近仍有资源的节点上建新矿机,铺两段短带绕过已有建筑,再用分拣器从侧面接进旧矿带。后续读到分拣器实际携带铁矿,磁铁仓重新增长,旧冶炼链才算恢复。

矿恢复了,磁线圈又卡在公共混料带上。铁块不断灌进传送带,末端仓库也满着,磁铁没有空位进入,制造台便一直缺料。多等一会儿没有帮助,上游还在继续把同一种东西塞进来。

这次先通过正常转移给仓库腾位置,再把供铁源仓搬空,等分拣器放下手里的货。趁它空载时配置过滤,暂时停止铁块继续灌入,然后把材料放回。旧铁块排出以后,磁铁终于能过去,磁线圈库存从 18 增长到了 60。

用到的是已有的 prepare_transfer / commit_transfer,以及配置工具的 sorter-filter 模式。当时先搬空源仓、等到完全空闲,是为了满足配置入口的安全条件,也防止改过滤时还有旧货攥在分拣器手里。后来允许“空载返程中的分拣器”安全改过滤,是下一篇物流阶段才补的能力。

这个处理有代价:依赖同一条铁块带的其他设备会暂时失去新供料,后面还得整理布局。它解决了眼前的堵塞,也暴露了早期公共带越接越复杂的问题。

原料通畅之后,动力引擎制造台在满供电下持续工作,专用输出仓从 9 个增加到 30 个。这条产品线也作为出发前的进度保存了下来。

伊卡洛斯也得学会停下来

在几个生产区之间跑来跑去时,上一篇提过的卡脚问题变得很具体。

有一次移动先正常走了约 6.5 米,然后位置就不再变化,能量却继续下降。旧实现还在等全局超时,Agent 看到的只是动作尚未结束。另一次更容易误判:工具已经返回移动成功,底层移动订单却没有正确结束,伊卡洛斯仍然小幅移动、持续耗电。

于是移动检查加了两个窗口:一段时间里有没有实际位移,以及到目标的距离有没有改善。完全没动要停,虽然动了却一直没有接近目标,也要停;断能则单独报告。结束动作时,还要确认清理的是这次提交给游戏的那个订单。

入口仍是 prepare_move / commit_move,改动在 Plugin 执行和收尾:持续观察位移、剩余距离与能量,并保留这次原生 OrderNode 的精确身份。停下时只终止自己下达的订单,不能扫掉玩家其他订单,也不能把“工具不再等待”当成“机甲已经停了”。Agent 再通过 get_action_result 等终态,并用 get_player_state 复读。

修复版部署后,同档有一次卡住在约 180 个游戏 tick,也就是约三秒时就被明确终止。复读时速度为零,核心能量仍是满的 400 MJ。这个样本证明了提前判停能工作,后面的路线仍然需要重新规划。

回充也不能只选一个“生产区附近”的旧坐标。一次走到这样的路点后,静止五秒只恢复了约 0.405 MJ,实际只有机甲自身的低速恢复。重新读取无线输电塔的位置,走到真正覆盖范围内,八秒才净增加约 20.8 MJ,之后充满。

所以长途出发前,要先看核心能量、燃料和真实充电点;到达后,再看位置、速度和能量趋势。这个流程在母星上就得做好,否则飞到没有现成电网的地方,只会更难收拾。

准备燃料时还发现过一个参数陷阱:煤矿机的工厂 objectId 不能直接当作手采的资源 nodeId——同一个数字换到矿脉池里,对应的可能是远处另一座铁矿。于是补强了 prepare_harvest 的参数说明和范围检查:从矿机的 resourceNodeIds 找到具体矿脉,再用 inspect_resource_node 核对类型与距离;目标在范围之外,就先移动接近。要防的就是选错对象之后,机甲长途追过去白白耗能。这个修改当时已通过构建和自动测试,新加的越界拒绝则留待后续部署复验。

出发前,蓝糖又堵了一次

正常保存、关闭游戏并恢复同一存档之后,出发准备期间又修了一次蓝糖供料。

为了改过 Plugin 之后还能接着这一局玩,此前还补过一对恢复工具:prepare_resume_owned_game / commit_resume_owned_game。恢复入口只接受受保护的一次性票据,由服务端核对保存身份和进度;Agent 不能传任意文件名,也不能挑另一个存档。早期恢复源的选择后来还出过问题,下一篇会接着记录这对工具的修正。

当时磁线圈和电路板共用一小段传送带。两边都在送料,但先来的原料很容易把短带占满。研究站缺另一种原料,无法开工,也就无法继续消耗已经到位的这一种;另一种原料又因为带上没有空位进不来。

拆成两条独立输入专线以后,蓝糖站恢复工作,下游基础化工研究的进度从 720 → 1123。原料已经一路送到消耗蓝糖的科研站,这次供料修复才有了结果。

这段时间还把逐存档 Journal 接进了工具。第一次手搓、第一次产线产出、第一次选择科技,开始分别留下记录,同时保存现实时间和本局时间。

这次是真的新增了一个只读工具:get_gameplay_journal。它把手搓产出、产线产出、科技与升级选择分别记录,并为每个存档独立保存首次事件。原因很实际:背包里的成品可能来自手搓或回收,库存快照本身说明不了第一次产出是怎么发生的;后续写日记需要能追到事件来源。

不过它是在这局已经运行约 20 小时 30 分钟时才挂上的。前面的蓝糖、红糖和动力引擎,能靠产线读回和保存记录证明做出来了,精确的首次产出时刻却没法补回来。旧历史就保留为未知,不能拿功能上线的时间替它们补一个“第一次”。

停在第一次搬钛之前

写到这里,母星已经有了基础冶炼、蓝糖、炼油与石墨、自动红糖和动力引擎。机甲核心 1、2 和驱动引擎 1、2 也已经按正常科研完成,供电、补给、移动判停和同档保存都有了实际处理经验。

下一步要去其他星球取得钛原料,为后续生产做准备。此时还没有跨星球运回的钛,也没有黄糖(结构矩阵)产线,更谈不上自动星际物流。

出发前先准备燃料、确认能量,并约定在真正起飞前单独保存一份检查点。航行如果失败,就从这次出发前的同一份检查点恢复。跨星球飞行、落地找矿和返程的过程,留到下一篇再写。

本文主体的产量、事故和时间边界整理自仓库中的存档日记 001经验账本。9 月 6 日的分拣器补记来自后续本机复验,单独保留其时间边界。

基础工具清单来自最早桥接版本的 MCP 定义。后续变化可对照红糖阶段的实现提交手采参数与范围修正逐存档 Journal 提交;事故复验汇总在问题与代码修复记录

← 回到归档