concepts - mclucy/lucy GitHub Wiki
核心概念
本页将说明 Lucy 的三个核心抽象:
- Package ID(包标识符)
- Platform / Source(平台与来源)
- Runtime Topology(运行时拓扑)
关键要点
Package ID(包标识符)
基本格式
在 Lucy 中,Package ID 是用于描述一个 package 的结构化字符串,标准形式为:
platform/project@version
注意,用户输入的原始 Package ID 并不一定具有唯一性。其唯一性会在内部被逐步解析并确保。目前这部分并没有统一入口,i.e.,正在设计。
示例:
fabric/[email protected]
↑ ↑ ↑
platform project version
neoforge/create@compatible
mcdr/mcdreforged@latest
lithium ← 省略 platform 与 version 的最简形式
字段规则与默认行为
platform / project / version 三段中,只有 project 必填。
- 省略
platform:Lucy 在运行时环境中推断。 - 省略
version:默认补为@compatible。
在实现中,Package ID 由 PackageId 结构体表示(见 types/type_id.go:124):
| 字段 | 类型 | 说明 |
|---|---|---|
Platform |
Platform |
平台枚举值;默认 PlatformAny(未指定) |
Name |
ProjectName |
项目 slug,如 fabric-api、lithium;大小写不敏感 |
Version |
RawVersion |
版本字符串;支持精确版本与特殊标记(@latest、@compatible) |
// ../lucy/types/type_id.go:124-128
type PackageId struct {
Platform Platform
Name ProjectName
Version RawVersion
}
Identity Package(单位包)
挪用了数学概念单位元(Identity Element)。
平台本身也可作为 package 安装或升级,这类包称为 identity package。
典型示例:
fabric/fabric或简写fabric:安装 Fabric 加载器minecraft:Minecraft 本体mcdreforged或mcdr:MCDReforged 插件框架
Lucy 会将别名标准化为规范包名(例如 fabric-loader -> fabric),并在版本可推断时自动补全为 @compatible(见 types/type_id.go:165)。
Platform(平台)与 Source(来源)
Platform(平台)
Platform 表示改变 Minecraft 原版行为的服务端框架或运行环境,可视为一组 package 的公共依赖。
平台的描述主体总是包而非服务器环境。这是与下文中的Topology的重要区分。
已知枚举值:
| 枚举常量 | 字符串值 | 说明 |
|---|---|---|
PlatformMinecraft |
minecraft |
原版 Minecraft(别名 PlatformVanilla) |
PlatformFabric |
fabric |
Fabric 模组加载器 |
PlatformForge |
forge |
Forge 模组加载器 |
PlatformNeoforge |
neoforge |
NeoForge 模组加载器 |
PlatformMCDR |
mcdr |
MCDReforged 插件框架 |
PlatformNone |
none |
无平台要求(被所有平台满足) |
PlatformAny |
"" |
未指定平台(单值占位,运行时收敛为具体平台) |
PlatformUnknown |
unknown |
解析失败哨兵值(不满足任何平台) |
将在未来通过去除特殊值和改变满足关系来重构为在 $p \leq r \equiv \text{p.Satisfy}(r)$ 上构成偏序集来确保 Satisfy() 的可靠性。
语义区分:
PlatformAny:尚未确定平台,但最终应收敛为某一个确定平台。PlatformNone:不要求任何特定平台,可被任意平台满足。PlatformUnknown:解析失败,既不被满足,也不满足任何平台。
见 types/type_id.go:58:
// ../lucy/types/type_id.go:16-28
type Platform string
const (
PlatformAny Platform = "" // PlatformAny is ambiguous but has single-valueness. It does NOT refer to multiple platforms, but rather a single platform that is unknown. Understand this as PlatformAny reduces to a definite platform at evaluation. Again, keep in mind that you should not allow it to be explicitly evaluated as multiple platforms.
PlatformMinecraft Platform = "minecraft"
PlatformVanilla = PlatformMinecraft // Alias for Minecraft
PlatformFabric Platform = "fabric"
PlatformForge Platform = "forge"
PlatformNeoforge Platform = "neoforge"
PlatformMCDR Platform = "mcdr"
PlatformNone Platform = "none" // PlatformNone is a special platform that is not satisfied by any platform, but it can satisfy all platforms. It is typically used to indicate the absence of a platform, for example, when a package is not compatible with any platform, or when a package does not require a platform.
PlatformUnknown Platform = "unknown" // PlatformUnknown is the only constant with no single-valueness, it can refer to multiple platforms other than the ones defined here.
)
// ../lucy/types/type_id.go:58-79
// Satisfy returns true if p satisfies the requirement of p2.
func (p Platform) Satisfy(p2 Platform) bool {
// When p2 is PlatformNone, it is satisfied by all platforms.
if p2 == PlatformNone {
return true
}
// PlatformUnknown is not satisfied by any platform, and does not satisfy
// any platform including itself.
if p == PlatformUnknown || p2 == PlatformUnknown {
return false
}
// When p2 is PlatformAny, it is satisfied by all platforms.
if p2 == PlatformAny {
return true
}
// When p is PlatformAny, it does not satisfy any platform except itself.
if p == PlatformAny {
return false
}
// Trivial cases
return p == p2
}
// ../lucy/types/type_id.go:95-97
func (p Platform) IsModding() bool {
return p == PlatformFabric || p == PlatformForge || p == PlatformNeoforge
}
Lucy 通过 IsModding() 区分 mod loader(fabric、forge、neoforge)与其他平台类型。
Source(来源)
Source 是 package 元数据上游的枚举标识。每一个具体 Source 对应一个 Provider。
- 用途:CLI 输入、配置存储、结果溯源
- 非用途:执行对象(执行对象是
upstream.Provider接口)
已知枚举值:
| 枚举常量 | 字符串值 | 说明 |
|---|---|---|
SourceModrinth |
modrinth |
Modrinth mod 目录 |
SourceCurseForge |
curseforge |
CurseForge mod 目录 |
SourceGitHub |
github |
GitHub Release 资产 |
SourceMCDR |
mcdr |
MCDReforged 插件目录 |
SourceAuto |
auto / "" |
路由策略标记,由路由层自动选择 provider |
SourceUnknown |
unknown |
解析失败哨兵值 |
Source 与 Platform 是正交维度:同一个 Fabric mod 可同时存在于 Modrinth 和 CurseForge。搜索命令可用 --source modrinth 限定来源(见 types/source.go:1)。
// ../lucy/types/source.go:16-25
const (
SourceAuto Source = iota // policy marker: let routing choose providers
SourceCurseForge
SourceModrinth
SourceGitHub
SourceMCDR
SourceUnknown // sentinel for parse/validation failure
)
版本标识符与兼容性(Compatibility)
RawVersion 与特殊版本标记
版本字段 RawVersion 除精确版本号外,还支持:
| 标记 | 内部常量 | 说明 |
|---|---|---|
@latest |
VersionLatest |
拉取该 project 最新发布版本,不考虑服务器环境兼容性 |
@compatible |
VersionCompatible |
拉取与当前服务器 Minecraft 版本兼容的最新版本(省略版本时默认值) |
| (省略) | VersionAny |
内部占位;等价于 @compatible,由 upstream 层推断后解析 |
@compatible 与 @latest 都是“可推断”版本(CanInfer() == true),在实际调用上游 API 前,应先经 upstream.InferVersion() 解析为具体版本号(见 types/type_dependency.go:30)。
[!WARNING] 以下内容基于非完整代码推断,可能与实际预期行为存在偏差。
下面关于 @compatible 解析机制的描述基于代码结构推断,未被行内文档记录。请以 upstream/ 目录中的实际实现为准。
@compatible 的解析依赖 probe 模块给出的当前服务器 Minecraft 游戏版本(GameVersion)。路由层基于该版本过滤上游目录并选出兼容的最新包版本。这也是推荐默认策略,可降低版本不匹配导致的运行时崩溃风险。
兼容性裁定(CompatVerdict)
Lucy 使用 CompatVerdict 枚举表达当前环境下的兼容性评估:
| 值 | 说明 |
|---|---|
compatible |
完全兼容,可正常安装 |
degraded |
部分兼容,可安装但存在风险(如通过 bridge 层适配) |
incompatible |
不兼容,无法安装 |
unresolved |
无法确定(topology 信息不足) |
CompatResult 除裁定值外,还携带:
- 机器可读原因:
Reason - 详细说明:
Detail - 风险等级:
RiskLevel(0-4,对应RiskNone至RiskCritical)
见 types/type_server_topology.go:44:
// ../lucy/types/type_server_topology.go:42-49
type CompatVerdict string
const (
CompatCompatible CompatVerdict = "compatible"
CompatDegraded CompatVerdict = "degraded"
CompatIncompatible CompatVerdict = "incompatible"
CompatUnresolved CompatVerdict = "unresolved"
)
// ../lucy/types/type_server_topology.go:51-56
type CompatResult struct {
Verdict CompatVerdict `json:"verdict"`
Reason string `json:"reason"`
Detail string `json:"detail"`
RiskLevel RuntimeRiskLevel `json:"risk_level"`
}
Runtime Topology(运行时拓扑)
Runtime Topology 是 probe 模块对当前服务器运行时结构的完整建模。Lucy 基于该模型判断 package 是否可安装、风险如何。
数据结构总览
RuntimeTopology 由三部分组成:
RuntimeTopology
├── PrimaryNode : RuntimeNodeID ← 主节点 ID(服务器核心运行时)
├── Nodes : []RuntimeNode ← 所有已知运行时节点
└── Edges : []RuntimeEdge ← 节点间关系边
RuntimeNode 表示运行时中的一个软件单元,字段如下(见 types/type_server_topology.go:73):
| 字段 | 说明 |
|---|---|
ID |
节点唯一标识(RuntimeNodeID) |
Role |
节点角色(见下节 RuntimeRole) |
IdentityPlatform |
节点对应的 Lucy Platform |
Capabilities |
节点可加载的 package 生态系统列表 |
RiskLevel |
节点已知风险等级(0-4) |
节点角色(RuntimeRole)
| 角色值 | 说明 |
|---|---|
mod_loader |
模组加载器(Fabric、Forge、NeoForge) |
plugin_core |
插件核心(MCDR、Paper、Spigot、Bukkit) |
hybrid |
混合服务端,同时支持 mod 与 Bukkit 插件(如 Arclight、Youer) |
proxy |
代理服务端(Velocity、BungeeCord、Waterfall) |
bridge |
跨生态桥接层(Connector、Kilt) |
protocol_bridge |
协议转换桥接层(Geyser) |
vanilla |
原版 Minecraft |
见 types/type_server_topology.go:7 与 probe/probe_topology_registry_data.go:29。
运行时能力(RuntimeCapability)
每个节点声明其可加载的 package 生态系统:
| Capability 值 | 说明 |
|---|---|
fabric_mods |
可加载 Fabric 模组 |
forge_mods |
可加载 Forge 模组 |
neoforge_mods |
可加载 NeoForge 模组 |
bukkit_plugins |
可加载 Bukkit/Spigot/Paper 插件 |
mcdr_plugins |
可加载 MCDReforged 插件 |
proxying |
代理转发能力 |
protocol_bridge |
协议桥接能力(如基岩版 <-> Java 版) |
见 types/type_server_topology.go:20。
节点关系边(RuntimeEdge)
边用于表达运行时节点关系(尤其是混合服务端与 bridge 场景):
边类型(RuntimeEdgeKind) |
含义 |
|---|---|
hosts |
一个节点托管另一个节点的 package 生态 |
bridges |
一个节点桥接另一个节点的 package 生态(高风险) |
routes |
流量路由关系(代理场景) |
adapts |
适配关系 |
见 types/type_server_topology.go:93。
// ../lucy/types/type_server_topology.go:73-79
type RuntimeNode struct {
ID RuntimeNodeID `json:"id"`
Role RuntimeRole `json:"role"`
IdentityPlatform Platform `json:"identity_platform"`
Capabilities []RuntimeCapability `json:"capabilities"`
RiskLevel RuntimeRiskLevel `json:"risk_level"`
}
// ../lucy/types/type_server_topology.go:102-107
type RuntimeEdge struct {
From RuntimeNodeID `json:"from"`
To RuntimeNodeID `json:"to"`
Kind RuntimeEdgeKind `json:"kind"`
Risk RuntimeRiskLevel `json:"risk"`
}
// ../lucy/types/type_server_topology.go:109-113
type RuntimeTopology struct {
PrimaryNode RuntimeNodeID `json:"primary_node"`
Nodes []RuntimeNode `json:"nodes"`
Edges []RuntimeEdge `json:"edges"`
}
// ../lucy/types/type_server_topology.go:124-126
func (t *RuntimeTopology) Resolved() bool {
return t != nil && t.PrimaryNode != RuntimeNodeUnknown && len(t.Nodes) > 0
}
// ../lucy/types/type_server_topology.go:128-140
func (t *RuntimeTopology) FindNode(id RuntimeNodeID) (RuntimeNode, bool) {
if t == nil {
return RuntimeNode{}, false
}
for _, node := range t.Nodes {
if node.ID == id {
return node, true
}
}
return RuntimeNode{}, false
}
注册表与默认 Topology
RuntimeRegistry 是静态注册表,用于保存已知平台的 topology 配置(RegistryEntry),支持按节点 ID 或 Platform 查询。
DefaultRegistry 内置的运行时节点包含:
minecraft、fabric、forge、neoforge、mcdr、paper、spigot、bukkit、folia、arclight、youer、velocity、bungeecord、waterfall、geyser、connector、kilt
BuildTopologyFromEntry() 会从单个 RegistryEntry 出发,遍历其 PolicyEdges,构建包含主节点及关联节点/边的完整 RuntimeTopology(见 probe/probe_topology_registry.go:86)。
[!WARNING] 以下内容基于非完整代码推断,可能与实际预期行为存在偏差。
下面关于 topology 与兼容性裁定协作机制的说明基于代码结构推断,未被行内文档记录。请以 probe/ 与 install/ 目录中的实际实现为准。
在安装流程开始时,probe 模块会扫描本地服务器目录,识别可执行文件与已安装 package 元数据,生成当前服务器的 RuntimeTopology。随后该 topology 传递到路由层,用于:
- 选择合适的上游 provider
- 过滤与当前平台不兼容的 package 版本
- 生成
CompatResult兼容性裁定
相关页面
参考文件
本页主要依据如下源码(基线 commit:86d3480cffa821b9b9c0747263a637b2973a7366):
README.md:150- 核心概念定义(Platform、Project、Package、Package ID 格式)types/type_id.go:16-Platform枚举完整定义及Satisfy()语义说明types/type_id.go:99-ProjectName类型及 slug 规范types/type_id.go:124-PackageId结构体及字符串化方法types/type_id.go:165- Identity package 映射表(别名 -> 规范名)types/source.go:1-Source枚举及SourceAuto路由策略标记语义types/type_dependency.go:7-RawVersion及VersionLatest/VersionCompatible常量types/type_dependency.go:30-CanInfer()方法(可推断版本集合)types/type_server_topology.go:7-RuntimeRole枚举types/type_server_topology.go:20-RuntimeCapability枚举types/type_server_topology.go:44-CompatVerdict、CompatResult、CompatPolicytypes/type_server_topology.go:73-RuntimeNode结构体types/type_server_topology.go:93-RuntimeEdgeKind枚举types/type_server_topology.go:109-RuntimeTopology结构体probe/probe_topology_registry.go:24-RuntimeRegistry注册表实现probe/probe_topology_registry.go:86-BuildTopologyFromEntry()拓扑构建逻辑probe/probe_topology_registry_data.go:29-defaultRegistryEntries默认注册表数据