Load only the LoRAs the user picked on Klein; do not require snofs.
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
+38
-1
@@ -16,16 +16,52 @@ export const LORA_STRENGTH_DEFAULT = 1
|
||||
export const LORA_STRENGTH_STEP = 0.05
|
||||
export const LORA_STACK_MAX = 8
|
||||
|
||||
/** Graph system LoRA for MiniMax turbo. Not a user pick. */
|
||||
export const MINIMAX_TURBO_LORA = 'minimax_h3_fl2v_turbo_8step_v1.0_comfyui_bf16.safetensors'
|
||||
|
||||
export function loraBasename(name: string) {
|
||||
const trimmed = String(name || '').trim().replace(/\\/g, '/')
|
||||
const parts = trimmed.split('/').filter(Boolean)
|
||||
return parts[parts.length - 1] || trimmed
|
||||
}
|
||||
|
||||
export function loraIdentityKey(name: string) {
|
||||
return loraBasename(name).replace(/^xaigen-?/i, '').toLowerCase()
|
||||
}
|
||||
|
||||
export function isXaigenOnlyLora(name: string) {
|
||||
return /^xaigen/i.test(loraBasename(name))
|
||||
}
|
||||
|
||||
/** Pick the real Comfy filename: exact path, then same basename ignoring `xaigen-`, then suffix/contains. */
|
||||
export function resolveComfyLoraName(wanted: string, available: string[]) {
|
||||
const target = String(wanted || '').trim().replace(/\\/g, '/')
|
||||
if (!target) return ''
|
||||
if (!available.length) return target
|
||||
const targetLower = target.toLowerCase()
|
||||
const exact = available.find(item => item.replace(/\\/g, '/') === target)
|
||||
if (exact) return exact
|
||||
const exactCi = available.find(item => item.replace(/\\/g, '/').toLowerCase() === targetLower)
|
||||
if (exactCi) return exactCi
|
||||
|
||||
const identity = loraIdentityKey(target)
|
||||
const identityHit = available.find(item => loraIdentityKey(item) === identity)
|
||||
if (identityHit) return identityHit
|
||||
|
||||
const stem = identity.replace(/\.(safetensors|sft|ckpt|pt|bin)$/i, '')
|
||||
if (!stem) return target
|
||||
const containsHits = available.filter((item) => {
|
||||
const base = loraBasename(item).toLowerCase()
|
||||
return base.includes(stem) || loraIdentityKey(item).includes(stem)
|
||||
})
|
||||
if (!containsHits.length) return target
|
||||
const suffix = containsHits.find((item) => {
|
||||
const base = loraBasename(item).toLowerCase()
|
||||
return base.endsWith(identity) || base.endsWith(stem) || loraIdentityKey(item).endsWith(identity)
|
||||
})
|
||||
return suffix || containsHits[0]
|
||||
}
|
||||
|
||||
export function loraDisplayName(name: string) {
|
||||
return loraBasename(name).replace(/\.(safetensors|sft|ckpt|pt|bin)$/i, '')
|
||||
}
|
||||
@@ -106,7 +142,7 @@ export function normalizeLoraStack(raw: unknown): LoraStackItem[] {
|
||||
if (out.length >= LORA_STACK_MAX) break
|
||||
const item = parseStackEntry(entry)
|
||||
if (!item) continue
|
||||
const key = loraKey(item.name)
|
||||
const key = loraIdentityKey(item.name)
|
||||
if (seen.has(key)) continue
|
||||
seen.add(key)
|
||||
out.push(item)
|
||||
@@ -159,6 +195,7 @@ export function loraStacksEqual(a?: unknown, b?: unknown) {
|
||||
))
|
||||
}
|
||||
|
||||
/** User LoRA picker only. `xaigen-*` names are visible only on xAIGen. */
|
||||
export function filterLorasForStudio(names: string[], xaigenStudio: boolean) {
|
||||
const seen = new Set<string>()
|
||||
const out: string[] = []
|
||||
|
||||
Reference in New Issue
Block a user