mirror of
https://github.com/moltbot/moltbot.git
synced 2026-05-07 07:58:36 +00:00
fix: prune stale plugin runtime symlinks
This commit is contained in:
@@ -252,7 +252,7 @@ legacy_runtime_deps_symlink_plugin() {
|
||||
|
||||
legacy_runtime_deps_symlink_target() {
|
||||
local plugin="$1"
|
||||
printf '%s/dist/extensions/%s/node_modules\n' "$(package_root)" "$plugin"
|
||||
printf '%s/@openclaw-upgrade-survivor/%s-runtime-dep\n' "$(dirname "$(package_root)")" "$plugin"
|
||||
}
|
||||
|
||||
legacy_runtime_deps_symlink_source() {
|
||||
@@ -431,6 +431,7 @@ seed_legacy_runtime_deps_symlink() {
|
||||
source_dir="$(legacy_runtime_deps_symlink_source "$plugin")"
|
||||
target_dir="$(legacy_runtime_deps_symlink_target "$plugin")"
|
||||
mkdir -p "$source_dir"
|
||||
mkdir -p "$(dirname "$target_dir")"
|
||||
printf '{"name":"openclaw-upgrade-survivor-legacy-runtime-deps","version":"0.0.0"}\n' \
|
||||
>"$source_dir/package.json"
|
||||
rm -rf "$target_dir"
|
||||
|
||||
@@ -11,6 +11,7 @@ import {
|
||||
openSync,
|
||||
readdirSync,
|
||||
readFileSync,
|
||||
readlinkSync,
|
||||
realpathSync,
|
||||
renameSync,
|
||||
rmdirSync,
|
||||
@@ -366,13 +367,101 @@ export function collectLegacyPluginRuntimeDepsStateRoots(params = {}) {
|
||||
);
|
||||
}
|
||||
|
||||
function isPathInsideRoot(candidate, root) {
|
||||
const relativePath = relative(root, candidate);
|
||||
return relativePath === "" || (!relativePath.startsWith("..") && !isAbsolute(relativePath));
|
||||
}
|
||||
|
||||
function collectLegacyPluginRuntimeDepsSymlinkPaths(roots, params = {}) {
|
||||
const packageRoot = params.packageRoot ?? DEFAULT_PACKAGE_ROOT;
|
||||
const readDir = params.readdirSync ?? readdirSync;
|
||||
const pathLstat = params.lstatSync ?? lstatSync;
|
||||
const readLink = params.readlinkSync ?? readlinkSync;
|
||||
const pathExists = params.existsSync ?? existsSync;
|
||||
const containingNodeModules = dirname(packageRoot);
|
||||
if (basename(containingNodeModules) !== "node_modules") {
|
||||
return [];
|
||||
}
|
||||
|
||||
const normalizedRoots = roots.map((root) => pathResolve(root));
|
||||
const candidates = [];
|
||||
function addCandidate(linkPath) {
|
||||
let linkStat;
|
||||
try {
|
||||
linkStat = pathLstat(linkPath);
|
||||
} catch {
|
||||
return;
|
||||
}
|
||||
if (!linkStat.isSymbolicLink()) {
|
||||
return;
|
||||
}
|
||||
let target;
|
||||
try {
|
||||
target = readLink(linkPath);
|
||||
} catch {
|
||||
return;
|
||||
}
|
||||
if (!target.includes(LEGACY_PLUGIN_RUNTIME_DEPS_DIR)) {
|
||||
return;
|
||||
}
|
||||
const resolvedTarget = pathResolve(dirname(linkPath), target);
|
||||
const pointsIntoPrunedRoot = normalizedRoots.some((root) =>
|
||||
isPathInsideRoot(resolvedTarget, root),
|
||||
);
|
||||
if (pointsIntoPrunedRoot || !pathExists(resolvedTarget)) {
|
||||
candidates.push(linkPath);
|
||||
}
|
||||
}
|
||||
|
||||
let entries;
|
||||
try {
|
||||
entries = readDir(containingNodeModules, { withFileTypes: true });
|
||||
} catch {
|
||||
return [];
|
||||
}
|
||||
for (const entry of entries) {
|
||||
if (entry.isDirectory() && entry.name.startsWith("@")) {
|
||||
const scopeDir = join(containingNodeModules, entry.name);
|
||||
let scopeEntries;
|
||||
try {
|
||||
scopeEntries = readDir(scopeDir, { withFileTypes: true });
|
||||
} catch {
|
||||
continue;
|
||||
}
|
||||
for (const scopeEntry of scopeEntries) {
|
||||
addCandidate(join(scopeDir, scopeEntry.name));
|
||||
}
|
||||
continue;
|
||||
}
|
||||
if (entry.isSymbolicLink()) {
|
||||
addCandidate(join(containingNodeModules, entry.name));
|
||||
}
|
||||
}
|
||||
return [...new Set(candidates.map((entry) => pathResolve(entry)))].toSorted((left, right) =>
|
||||
left.localeCompare(right),
|
||||
);
|
||||
}
|
||||
|
||||
export function pruneLegacyPluginRuntimeDepsState(params = {}) {
|
||||
const pathExists = params.existsSync ?? existsSync;
|
||||
const removePath = params.rmSync ?? rmSync;
|
||||
const log = params.log ?? console;
|
||||
const removed = [];
|
||||
const removedSymlinks = [];
|
||||
const roots = collectLegacyPluginRuntimeDepsStateRoots(params);
|
||||
|
||||
for (const root of collectLegacyPluginRuntimeDepsStateRoots(params)) {
|
||||
for (const linkPath of collectLegacyPluginRuntimeDepsSymlinkPaths(roots, params)) {
|
||||
try {
|
||||
removePath(linkPath, { force: true });
|
||||
removedSymlinks.push(linkPath);
|
||||
} catch (error) {
|
||||
log.warn?.(
|
||||
`[postinstall] could not prune legacy plugin runtime deps symlink ${linkPath}: ${String(error)}`,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
for (const root of roots) {
|
||||
if (!pathExists(root)) {
|
||||
continue;
|
||||
}
|
||||
@@ -389,6 +478,11 @@ export function pruneLegacyPluginRuntimeDepsState(params = {}) {
|
||||
if (removed.length > 0) {
|
||||
log.log?.(`[postinstall] pruned legacy plugin runtime deps: ${removed.join(", ")}`);
|
||||
}
|
||||
if (removedSymlinks.length > 0) {
|
||||
log.log?.(
|
||||
`[postinstall] pruned legacy plugin runtime deps symlinks: ${removedSymlinks.join(", ")}`,
|
||||
);
|
||||
}
|
||||
|
||||
return removed;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user