mirror of
https://github.com/openclaw/openclaw.git
synced 2026-05-08 21:38:25 +00:00
chore: Enable "curly" rule to avoid single-statement if confusion/errors.
This commit is contained in:
@@ -4,13 +4,17 @@ import { fileURLToPath } from "node:url";
|
||||
|
||||
export function resolveBundledSkillsDir(): string | undefined {
|
||||
const override = process.env.OPENCLAW_BUNDLED_SKILLS_DIR?.trim();
|
||||
if (override) return override;
|
||||
if (override) {
|
||||
return override;
|
||||
}
|
||||
|
||||
// bun --compile: ship a sibling `skills/` next to the executable.
|
||||
try {
|
||||
const execDir = path.dirname(process.execPath);
|
||||
const sibling = path.join(execDir, "skills");
|
||||
if (fs.existsSync(sibling)) return sibling;
|
||||
if (fs.existsSync(sibling)) {
|
||||
return sibling;
|
||||
}
|
||||
} catch {
|
||||
// ignore
|
||||
}
|
||||
@@ -20,7 +24,9 @@ export function resolveBundledSkillsDir(): string | undefined {
|
||||
const moduleDir = path.dirname(fileURLToPath(import.meta.url));
|
||||
const root = path.resolve(moduleDir, "..", "..", "..");
|
||||
const candidate = path.join(root, "skills");
|
||||
if (fs.existsSync(candidate)) return candidate;
|
||||
if (fs.existsSync(candidate)) {
|
||||
return candidate;
|
||||
}
|
||||
} catch {
|
||||
// ignore
|
||||
}
|
||||
|
||||
@@ -10,10 +10,18 @@ const DEFAULT_CONFIG_VALUES: Record<string, boolean> = {
|
||||
};
|
||||
|
||||
function isTruthy(value: unknown): boolean {
|
||||
if (value === undefined || value === null) return false;
|
||||
if (typeof value === "boolean") return value;
|
||||
if (typeof value === "number") return value !== 0;
|
||||
if (typeof value === "string") return value.trim().length > 0;
|
||||
if (value === undefined || value === null) {
|
||||
return false;
|
||||
}
|
||||
if (typeof value === "boolean") {
|
||||
return value;
|
||||
}
|
||||
if (typeof value === "number") {
|
||||
return value !== 0;
|
||||
}
|
||||
if (typeof value === "string") {
|
||||
return value.trim().length > 0;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -21,7 +29,9 @@ export function resolveConfigPath(config: OpenClawConfig | undefined, pathStr: s
|
||||
const parts = pathStr.split(".").filter(Boolean);
|
||||
let current: unknown = config;
|
||||
for (const part of parts) {
|
||||
if (typeof current !== "object" || current === null) return undefined;
|
||||
if (typeof current !== "object" || current === null) {
|
||||
return undefined;
|
||||
}
|
||||
current = (current as Record<string, unknown>)[part];
|
||||
}
|
||||
return current;
|
||||
@@ -40,9 +50,13 @@ export function resolveSkillConfig(
|
||||
skillKey: string,
|
||||
): SkillConfig | undefined {
|
||||
const skills = config?.skills?.entries;
|
||||
if (!skills || typeof skills !== "object") return undefined;
|
||||
if (!skills || typeof skills !== "object") {
|
||||
return undefined;
|
||||
}
|
||||
const entry = (skills as Record<string, SkillConfig | undefined>)[skillKey];
|
||||
if (!entry || typeof entry !== "object") return undefined;
|
||||
if (!entry || typeof entry !== "object") {
|
||||
return undefined;
|
||||
}
|
||||
return entry;
|
||||
}
|
||||
|
||||
@@ -51,8 +65,12 @@ export function resolveRuntimePlatform(): string {
|
||||
}
|
||||
|
||||
function normalizeAllowlist(input: unknown): string[] | undefined {
|
||||
if (!input) return undefined;
|
||||
if (!Array.isArray(input)) return undefined;
|
||||
if (!input) {
|
||||
return undefined;
|
||||
}
|
||||
if (!Array.isArray(input)) {
|
||||
return undefined;
|
||||
}
|
||||
const normalized = input.map((entry) => String(entry).trim()).filter(Boolean);
|
||||
return normalized.length > 0 ? normalized : undefined;
|
||||
}
|
||||
@@ -68,8 +86,12 @@ export function resolveBundledAllowlist(config?: OpenClawConfig): string[] | und
|
||||
}
|
||||
|
||||
export function isBundledSkillAllowed(entry: SkillEntry, allowlist?: string[]): boolean {
|
||||
if (!allowlist || allowlist.length === 0) return true;
|
||||
if (!isBundledSkill(entry)) return true;
|
||||
if (!allowlist || allowlist.length === 0) {
|
||||
return true;
|
||||
}
|
||||
if (!isBundledSkill(entry)) {
|
||||
return true;
|
||||
}
|
||||
const key = resolveSkillKey(entry.skill, entry);
|
||||
return allowlist.includes(key) || allowlist.includes(entry.skill.name);
|
||||
}
|
||||
@@ -101,8 +123,12 @@ export function shouldIncludeSkill(params: {
|
||||
const osList = entry.metadata?.os ?? [];
|
||||
const remotePlatforms = eligibility?.remote?.platforms ?? [];
|
||||
|
||||
if (skillConfig?.enabled === false) return false;
|
||||
if (!isBundledSkillAllowed(entry, allowBundled)) return false;
|
||||
if (skillConfig?.enabled === false) {
|
||||
return false;
|
||||
}
|
||||
if (!isBundledSkillAllowed(entry, allowBundled)) {
|
||||
return false;
|
||||
}
|
||||
if (
|
||||
osList.length > 0 &&
|
||||
!osList.includes(resolveRuntimePlatform()) &&
|
||||
@@ -117,8 +143,12 @@ export function shouldIncludeSkill(params: {
|
||||
const requiredBins = entry.metadata?.requires?.bins ?? [];
|
||||
if (requiredBins.length > 0) {
|
||||
for (const bin of requiredBins) {
|
||||
if (hasBinary(bin)) continue;
|
||||
if (eligibility?.remote?.hasBin?.(bin)) continue;
|
||||
if (hasBinary(bin)) {
|
||||
continue;
|
||||
}
|
||||
if (eligibility?.remote?.hasBin?.(bin)) {
|
||||
continue;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@@ -127,14 +157,20 @@ export function shouldIncludeSkill(params: {
|
||||
const anyFound =
|
||||
requiredAnyBins.some((bin) => hasBinary(bin)) ||
|
||||
eligibility?.remote?.hasAnyBin?.(requiredAnyBins);
|
||||
if (!anyFound) return false;
|
||||
if (!anyFound) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
const requiredEnv = entry.metadata?.requires?.env ?? [];
|
||||
if (requiredEnv.length > 0) {
|
||||
for (const envName of requiredEnv) {
|
||||
if (process.env[envName]) continue;
|
||||
if (skillConfig?.env?.[envName]) continue;
|
||||
if (process.env[envName]) {
|
||||
continue;
|
||||
}
|
||||
if (skillConfig?.env?.[envName]) {
|
||||
continue;
|
||||
}
|
||||
if (skillConfig?.apiKey && entry.metadata?.primaryEnv === envName) {
|
||||
continue;
|
||||
}
|
||||
@@ -145,7 +181,9 @@ export function shouldIncludeSkill(params: {
|
||||
const requiredConfig = entry.metadata?.requires?.config ?? [];
|
||||
if (requiredConfig.length > 0) {
|
||||
for (const configPath of requiredConfig) {
|
||||
if (!isConfigPathTruthy(config, configPath)) return false;
|
||||
if (!isConfigPathTruthy(config, configPath)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -10,11 +10,15 @@ export function applySkillEnvOverrides(params: { skills: SkillEntry[]; config?:
|
||||
for (const entry of skills) {
|
||||
const skillKey = resolveSkillKey(entry.skill, entry);
|
||||
const skillConfig = resolveSkillConfig(config, skillKey);
|
||||
if (!skillConfig) continue;
|
||||
if (!skillConfig) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (skillConfig.env) {
|
||||
for (const [envKey, envValue] of Object.entries(skillConfig.env)) {
|
||||
if (!envValue || process.env[envKey]) continue;
|
||||
if (!envValue || process.env[envKey]) {
|
||||
continue;
|
||||
}
|
||||
updates.push({ key: envKey, prev: process.env[envKey] });
|
||||
process.env[envKey] = envValue;
|
||||
}
|
||||
@@ -29,8 +33,11 @@ export function applySkillEnvOverrides(params: { skills: SkillEntry[]; config?:
|
||||
|
||||
return () => {
|
||||
for (const update of updates) {
|
||||
if (update.prev === undefined) delete process.env[update.key];
|
||||
else process.env[update.key] = update.prev;
|
||||
if (update.prev === undefined) {
|
||||
delete process.env[update.key];
|
||||
} else {
|
||||
process.env[update.key] = update.prev;
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
@@ -40,16 +47,22 @@ export function applySkillEnvOverridesFromSnapshot(params: {
|
||||
config?: OpenClawConfig;
|
||||
}) {
|
||||
const { snapshot, config } = params;
|
||||
if (!snapshot) return () => {};
|
||||
if (!snapshot) {
|
||||
return () => {};
|
||||
}
|
||||
const updates: Array<{ key: string; prev: string | undefined }> = [];
|
||||
|
||||
for (const skill of snapshot.skills) {
|
||||
const skillConfig = resolveSkillConfig(config, skill.name);
|
||||
if (!skillConfig) continue;
|
||||
if (!skillConfig) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (skillConfig.env) {
|
||||
for (const [envKey, envValue] of Object.entries(skillConfig.env)) {
|
||||
if (!envValue || process.env[envKey]) continue;
|
||||
if (!envValue || process.env[envKey]) {
|
||||
continue;
|
||||
}
|
||||
updates.push({ key: envKey, prev: process.env[envKey] });
|
||||
process.env[envKey] = envValue;
|
||||
}
|
||||
@@ -66,8 +79,11 @@ export function applySkillEnvOverridesFromSnapshot(params: {
|
||||
|
||||
return () => {
|
||||
for (const update of updates) {
|
||||
if (update.prev === undefined) delete process.env[update.key];
|
||||
else process.env[update.key] = update.prev;
|
||||
if (update.prev === undefined) {
|
||||
delete process.env[update.key];
|
||||
} else {
|
||||
process.env[update.key] = update.prev;
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@@ -17,7 +17,9 @@ export function parseFrontmatter(content: string): ParsedSkillFrontmatter {
|
||||
}
|
||||
|
||||
function normalizeStringList(input: unknown): string[] {
|
||||
if (!input) return [];
|
||||
if (!input) {
|
||||
return [];
|
||||
}
|
||||
if (Array.isArray(input)) {
|
||||
return input.map((value) => String(value).trim()).filter(Boolean);
|
||||
}
|
||||
@@ -31,7 +33,9 @@ function normalizeStringList(input: unknown): string[] {
|
||||
}
|
||||
|
||||
function parseInstallSpec(input: unknown): SkillInstallSpec | undefined {
|
||||
if (!input || typeof input !== "object") return undefined;
|
||||
if (!input || typeof input !== "object") {
|
||||
return undefined;
|
||||
}
|
||||
const raw = input as Record<string, unknown>;
|
||||
const kindRaw =
|
||||
typeof raw.kind === "string" ? raw.kind : typeof raw.type === "string" ? raw.type : "";
|
||||
@@ -44,20 +48,44 @@ function parseInstallSpec(input: unknown): SkillInstallSpec | undefined {
|
||||
kind: kind,
|
||||
};
|
||||
|
||||
if (typeof raw.id === "string") spec.id = raw.id;
|
||||
if (typeof raw.label === "string") spec.label = raw.label;
|
||||
if (typeof raw.id === "string") {
|
||||
spec.id = raw.id;
|
||||
}
|
||||
if (typeof raw.label === "string") {
|
||||
spec.label = raw.label;
|
||||
}
|
||||
const bins = normalizeStringList(raw.bins);
|
||||
if (bins.length > 0) spec.bins = bins;
|
||||
if (bins.length > 0) {
|
||||
spec.bins = bins;
|
||||
}
|
||||
const osList = normalizeStringList(raw.os);
|
||||
if (osList.length > 0) spec.os = osList;
|
||||
if (typeof raw.formula === "string") spec.formula = raw.formula;
|
||||
if (typeof raw.package === "string") spec.package = raw.package;
|
||||
if (typeof raw.module === "string") spec.module = raw.module;
|
||||
if (typeof raw.url === "string") spec.url = raw.url;
|
||||
if (typeof raw.archive === "string") spec.archive = raw.archive;
|
||||
if (typeof raw.extract === "boolean") spec.extract = raw.extract;
|
||||
if (typeof raw.stripComponents === "number") spec.stripComponents = raw.stripComponents;
|
||||
if (typeof raw.targetDir === "string") spec.targetDir = raw.targetDir;
|
||||
if (osList.length > 0) {
|
||||
spec.os = osList;
|
||||
}
|
||||
if (typeof raw.formula === "string") {
|
||||
spec.formula = raw.formula;
|
||||
}
|
||||
if (typeof raw.package === "string") {
|
||||
spec.package = raw.package;
|
||||
}
|
||||
if (typeof raw.module === "string") {
|
||||
spec.module = raw.module;
|
||||
}
|
||||
if (typeof raw.url === "string") {
|
||||
spec.url = raw.url;
|
||||
}
|
||||
if (typeof raw.archive === "string") {
|
||||
spec.archive = raw.archive;
|
||||
}
|
||||
if (typeof raw.extract === "boolean") {
|
||||
spec.extract = raw.extract;
|
||||
}
|
||||
if (typeof raw.stripComponents === "number") {
|
||||
spec.stripComponents = raw.stripComponents;
|
||||
}
|
||||
if (typeof raw.targetDir === "string") {
|
||||
spec.targetDir = raw.targetDir;
|
||||
}
|
||||
|
||||
return spec;
|
||||
}
|
||||
@@ -76,10 +104,14 @@ export function resolveOpenClawMetadata(
|
||||
frontmatter: ParsedSkillFrontmatter,
|
||||
): OpenClawSkillMetadata | undefined {
|
||||
const raw = getFrontmatterValue(frontmatter, "metadata");
|
||||
if (!raw) return undefined;
|
||||
if (!raw) {
|
||||
return undefined;
|
||||
}
|
||||
try {
|
||||
const parsed = JSON5.parse(raw);
|
||||
if (!parsed || typeof parsed !== "object") return undefined;
|
||||
if (!parsed || typeof parsed !== "object") {
|
||||
return undefined;
|
||||
}
|
||||
const metadataRawCandidates = [MANIFEST_KEY, ...LEGACY_MANIFEST_KEYS];
|
||||
let metadataRaw: unknown;
|
||||
for (const key of metadataRawCandidates) {
|
||||
@@ -89,7 +121,9 @@ export function resolveOpenClawMetadata(
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!metadataRaw || typeof metadataRaw !== "object") return undefined;
|
||||
if (!metadataRaw || typeof metadataRaw !== "object") {
|
||||
return undefined;
|
||||
}
|
||||
const metadataObj = metadataRaw as Record<string, unknown>;
|
||||
const requiresRaw =
|
||||
typeof metadataObj.requires === "object" && metadataObj.requires !== null
|
||||
|
||||
@@ -17,12 +17,16 @@ export function resolvePluginSkillDirs(params: {
|
||||
config?: OpenClawConfig;
|
||||
}): string[] {
|
||||
const workspaceDir = params.workspaceDir.trim();
|
||||
if (!workspaceDir) return [];
|
||||
if (!workspaceDir) {
|
||||
return [];
|
||||
}
|
||||
const registry = loadPluginManifestRegistry({
|
||||
workspaceDir,
|
||||
config: params.config,
|
||||
});
|
||||
if (registry.plugins.length === 0) return [];
|
||||
if (registry.plugins.length === 0) {
|
||||
return [];
|
||||
}
|
||||
const normalizedPlugins = normalizePluginsConfig(params.config?.plugins);
|
||||
const memorySlot = normalizedPlugins.slots.memory;
|
||||
let selectedMemoryPluginId: string | null = null;
|
||||
@@ -30,28 +34,38 @@ export function resolvePluginSkillDirs(params: {
|
||||
const resolved: string[] = [];
|
||||
|
||||
for (const record of registry.plugins) {
|
||||
if (!record.skills || record.skills.length === 0) continue;
|
||||
if (!record.skills || record.skills.length === 0) {
|
||||
continue;
|
||||
}
|
||||
const enableState = resolveEnableState(record.id, record.origin, normalizedPlugins);
|
||||
if (!enableState.enabled) continue;
|
||||
if (!enableState.enabled) {
|
||||
continue;
|
||||
}
|
||||
const memoryDecision = resolveMemorySlotDecision({
|
||||
id: record.id,
|
||||
kind: record.kind,
|
||||
slot: memorySlot,
|
||||
selectedId: selectedMemoryPluginId,
|
||||
});
|
||||
if (!memoryDecision.enabled) continue;
|
||||
if (!memoryDecision.enabled) {
|
||||
continue;
|
||||
}
|
||||
if (memoryDecision.selected && record.kind === "memory") {
|
||||
selectedMemoryPluginId = record.id;
|
||||
}
|
||||
for (const raw of record.skills) {
|
||||
const trimmed = raw.trim();
|
||||
if (!trimmed) continue;
|
||||
if (!trimmed) {
|
||||
continue;
|
||||
}
|
||||
const candidate = path.resolve(record.rootDir, trimmed);
|
||||
if (!fs.existsSync(candidate)) {
|
||||
log.warn(`plugin skill path not found (${record.id}): ${candidate}`);
|
||||
continue;
|
||||
}
|
||||
if (seen.has(candidate)) continue;
|
||||
if (seen.has(candidate)) {
|
||||
continue;
|
||||
}
|
||||
seen.add(candidate);
|
||||
resolved.push(candidate);
|
||||
}
|
||||
|
||||
@@ -92,14 +92,18 @@ export function bumpSkillsSnapshotVersion(params?: {
|
||||
}
|
||||
|
||||
export function getSkillsSnapshotVersion(workspaceDir?: string): number {
|
||||
if (!workspaceDir) return globalVersion;
|
||||
if (!workspaceDir) {
|
||||
return globalVersion;
|
||||
}
|
||||
const local = workspaceVersions.get(workspaceDir) ?? 0;
|
||||
return Math.max(globalVersion, local);
|
||||
}
|
||||
|
||||
export function ensureSkillsWatcher(params: { workspaceDir: string; config?: OpenClawConfig }) {
|
||||
const workspaceDir = params.workspaceDir.trim();
|
||||
if (!workspaceDir) return;
|
||||
if (!workspaceDir) {
|
||||
return;
|
||||
}
|
||||
const watchEnabled = params.config?.skills?.load?.watch !== false;
|
||||
const debounceMsRaw = params.config?.skills?.load?.watchDebounceMs;
|
||||
const debounceMs =
|
||||
@@ -111,7 +115,9 @@ export function ensureSkillsWatcher(params: { workspaceDir: string; config?: Ope
|
||||
if (!watchEnabled) {
|
||||
if (existing) {
|
||||
watchers.delete(workspaceDir);
|
||||
if (existing.timer) clearTimeout(existing.timer);
|
||||
if (existing.timer) {
|
||||
clearTimeout(existing.timer);
|
||||
}
|
||||
void existing.watcher.close().catch(() => {});
|
||||
}
|
||||
return;
|
||||
@@ -124,7 +130,9 @@ export function ensureSkillsWatcher(params: { workspaceDir: string; config?: Ope
|
||||
}
|
||||
if (existing) {
|
||||
watchers.delete(workspaceDir);
|
||||
if (existing.timer) clearTimeout(existing.timer);
|
||||
if (existing.timer) {
|
||||
clearTimeout(existing.timer);
|
||||
}
|
||||
void existing.watcher.close().catch(() => {});
|
||||
}
|
||||
|
||||
@@ -143,7 +151,9 @@ export function ensureSkillsWatcher(params: { workspaceDir: string; config?: Ope
|
||||
|
||||
const schedule = (changedPath?: string) => {
|
||||
state.pendingPath = changedPath ?? state.pendingPath;
|
||||
if (state.timer) clearTimeout(state.timer);
|
||||
if (state.timer) {
|
||||
clearTimeout(state.timer);
|
||||
}
|
||||
state.timer = setTimeout(() => {
|
||||
const pendingPath = state.pendingPath;
|
||||
state.pendingPath = undefined;
|
||||
|
||||
@@ -7,6 +7,8 @@ export async function serializeByKey<T>(key: string, task: () => Promise<T>) {
|
||||
try {
|
||||
return await next;
|
||||
} finally {
|
||||
if (SKILLS_SYNC_QUEUE.get(key) === next) SKILLS_SYNC_QUEUE.delete(key);
|
||||
if (SKILLS_SYNC_QUEUE.get(key) === next) {
|
||||
SKILLS_SYNC_QUEUE.delete(key);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -36,7 +36,9 @@ function debugSkillCommandOnce(
|
||||
message: string,
|
||||
meta?: Record<string, unknown>,
|
||||
) {
|
||||
if (skillCommandDebugOnce.has(messageKey)) return;
|
||||
if (skillCommandDebugOnce.has(messageKey)) {
|
||||
return;
|
||||
}
|
||||
skillCommandDebugOnce.add(messageKey);
|
||||
skillsLogger.debug(message, meta);
|
||||
}
|
||||
@@ -79,14 +81,18 @@ function sanitizeSkillCommandName(raw: string): string {
|
||||
|
||||
function resolveUniqueSkillCommandName(base: string, used: Set<string>): string {
|
||||
const normalizedBase = base.toLowerCase();
|
||||
if (!used.has(normalizedBase)) return base;
|
||||
if (!used.has(normalizedBase)) {
|
||||
return base;
|
||||
}
|
||||
for (let index = 2; index < 1000; index += 1) {
|
||||
const suffix = `_${index}`;
|
||||
const maxBaseLength = Math.max(1, SKILL_COMMAND_MAX_LENGTH - suffix.length);
|
||||
const trimmedBase = base.slice(0, maxBaseLength);
|
||||
const candidate = `${trimmedBase}${suffix}`;
|
||||
const candidateKey = candidate.toLowerCase();
|
||||
if (!used.has(candidateKey)) return candidate;
|
||||
if (!used.has(candidateKey)) {
|
||||
return candidate;
|
||||
}
|
||||
}
|
||||
const fallback = `${base.slice(0, Math.max(1, SKILL_COMMAND_MAX_LENGTH - 2))}_x`;
|
||||
return fallback;
|
||||
@@ -102,7 +108,9 @@ function loadSkillEntries(
|
||||
): SkillEntry[] {
|
||||
const loadSkills = (params: { dir: string; source: string }): Skill[] => {
|
||||
const loaded = loadSkillsFromDir(params);
|
||||
if (Array.isArray(loaded)) return loaded;
|
||||
if (Array.isArray(loaded)) {
|
||||
return loaded;
|
||||
}
|
||||
if (
|
||||
loaded &&
|
||||
typeof loaded === "object" &&
|
||||
@@ -151,10 +159,18 @@ function loadSkillEntries(
|
||||
|
||||
const merged = new Map<string, Skill>();
|
||||
// Precedence: extra < bundled < managed < workspace
|
||||
for (const skill of extraSkills) merged.set(skill.name, skill);
|
||||
for (const skill of bundledSkills) merged.set(skill.name, skill);
|
||||
for (const skill of managedSkills) merged.set(skill.name, skill);
|
||||
for (const skill of workspaceSkills) merged.set(skill.name, skill);
|
||||
for (const skill of extraSkills) {
|
||||
merged.set(skill.name, skill);
|
||||
}
|
||||
for (const skill of bundledSkills) {
|
||||
merged.set(skill.name, skill);
|
||||
}
|
||||
for (const skill of managedSkills) {
|
||||
merged.set(skill.name, skill);
|
||||
}
|
||||
for (const skill of workspaceSkills) {
|
||||
merged.set(skill.name, skill);
|
||||
}
|
||||
|
||||
const skillEntries: SkillEntry[] = Array.from(merged.values()).map((skill) => {
|
||||
let frontmatter: ParsedSkillFrontmatter = {};
|
||||
@@ -246,7 +262,9 @@ export function resolveSkillsPromptForRun(params: {
|
||||
workspaceDir: string;
|
||||
}): string {
|
||||
const snapshotPrompt = params.skillsSnapshot?.prompt?.trim();
|
||||
if (snapshotPrompt) return snapshotPrompt;
|
||||
if (snapshotPrompt) {
|
||||
return snapshotPrompt;
|
||||
}
|
||||
if (params.entries && params.entries.length > 0) {
|
||||
const prompt = buildWorkspaceSkillsPrompt(params.workspaceDir, {
|
||||
entries: params.entries,
|
||||
@@ -277,7 +295,9 @@ export async function syncSkillsToWorkspace(params: {
|
||||
}) {
|
||||
const sourceDir = resolveUserPath(params.sourceWorkspaceDir);
|
||||
const targetDir = resolveUserPath(params.targetWorkspaceDir);
|
||||
if (sourceDir === targetDir) return;
|
||||
if (sourceDir === targetDir) {
|
||||
return;
|
||||
}
|
||||
|
||||
await serializeByKey(`syncSkills:${targetDir}`, async () => {
|
||||
const targetSkillsDir = path.join(targetDir, "skills");
|
||||
@@ -371,8 +391,12 @@ export function buildWorkspaceSkillCommandSpecs(
|
||||
)
|
||||
.trim()
|
||||
.toLowerCase();
|
||||
if (!kindRaw) return undefined;
|
||||
if (kindRaw !== "tool") return undefined;
|
||||
if (!kindRaw) {
|
||||
return undefined;
|
||||
}
|
||||
if (kindRaw !== "tool") {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
const toolName = (
|
||||
entry.frontmatter?.["command-tool"] ??
|
||||
|
||||
Reference in New Issue
Block a user