mirror of
https://github.com/Comfy-Org/ComfyUI_frontend.git
synced 2026-05-22 13:32:11 +00:00
refactor: consolidate Outcome types and replace push loops with flatMap
- proxyWidgetMigration.ts: collapse three *Result discriminated unions into a single Outcome<TOk, TReason>; merge quarantineFor into makeQuarantineEntry; SnapshotLink extends PrimitiveBypassTargetRef; rename cohortReferencesPrimitive -> cohortDuplicatesPrimitive and drop mutable counter - SubgraphNode.serialize: replace for+push+hasSerializableValue flag with flatMap and .some() - appModeStore: replace nested for+continue+push with nested flatMap Amp-Thread-ID: https://ampcode.com/threads/T-019e1f3a-a617-70b4-8945-3f0fbd34c1de Co-authored-by: Amp <amp@ampcode.com>
This commit is contained in:
@@ -268,32 +268,22 @@ function collectTargetsSkippingDangling(
|
||||
primitiveNode: LGraphNode
|
||||
): PrimitiveBypassTargetRef[] {
|
||||
const subgraph = hostNode.subgraph
|
||||
const output = primitiveNode.outputs?.[0]
|
||||
const linkIds = output?.links ?? []
|
||||
const targets: PrimitiveBypassTargetRef[] = []
|
||||
for (const linkId of linkIds) {
|
||||
const linkIds = primitiveNode.outputs?.[0]?.links ?? []
|
||||
return linkIds.flatMap((linkId) => {
|
||||
const link = subgraph.links.get(linkId)
|
||||
if (!link) continue
|
||||
targets.push({
|
||||
targetNodeId: link.target_id,
|
||||
targetSlot: link.target_slot
|
||||
})
|
||||
}
|
||||
return targets
|
||||
return link
|
||||
? [{ targetNodeId: link.target_id, targetSlot: link.target_slot }]
|
||||
: []
|
||||
})
|
||||
}
|
||||
|
||||
function cohortReferencesPrimitive(
|
||||
function cohortDuplicatesPrimitive(
|
||||
cohort: readonly LegacyProxyEntrySource[],
|
||||
primitiveNodeId: string
|
||||
): boolean {
|
||||
let count = 0
|
||||
for (const entry of cohort) {
|
||||
if (entry.sourceNodeId === primitiveNodeId) {
|
||||
count += 1
|
||||
if (count >= 2) return true
|
||||
}
|
||||
}
|
||||
return false
|
||||
return (
|
||||
cohort.filter((entry) => entry.sourceNodeId === primitiveNodeId).length >= 2
|
||||
)
|
||||
}
|
||||
|
||||
function classify(
|
||||
@@ -320,7 +310,7 @@ function classify(
|
||||
|
||||
if (sourceNode.type === PRIMITIVE_NODE_TYPE) {
|
||||
const targets = collectTargetsSkippingDangling(hostNode, sourceNode)
|
||||
const cohortDuplicated = cohortReferencesPrimitive(
|
||||
const cohortDuplicated = cohortDuplicatesPrimitive(
|
||||
cohort,
|
||||
normalized.sourceNodeId
|
||||
)
|
||||
@@ -382,9 +372,11 @@ function addUniqueSubgraphInput(
|
||||
return subgraph.addInput(uniqueName, type)
|
||||
}
|
||||
|
||||
type RepairValueResult =
|
||||
| { ok: true; subgraphInputName: string }
|
||||
| { ok: false; reason: ProxyWidgetQuarantineReason }
|
||||
type Outcome<TOk, TReason = ProxyWidgetQuarantineReason> =
|
||||
| ({ ok: true } & TOk)
|
||||
| { ok: false; reason: TReason }
|
||||
|
||||
type RepairValueResult = Outcome<{ subgraphInputName: string }>
|
||||
|
||||
function repairValue(
|
||||
hostNode: SubgraphNode,
|
||||
@@ -484,19 +476,18 @@ function repairCreateSubgraphInput(
|
||||
return { ok: true, subgraphInputName: newSubgraphInput.name }
|
||||
}
|
||||
|
||||
type RepairPrimitiveResult =
|
||||
| { ok: true; subgraphInputName: string; reconnectCount: number }
|
||||
| { ok: false; reason: 'primitiveBypassFailed' }
|
||||
type RepairPrimitiveResult = Outcome<
|
||||
{ subgraphInputName: string; reconnectCount: number },
|
||||
'primitiveBypassFailed'
|
||||
>
|
||||
|
||||
const PRIMITIVE_FAILED: RepairPrimitiveResult = {
|
||||
ok: false,
|
||||
reason: 'primitiveBypassFailed'
|
||||
}
|
||||
|
||||
interface SnapshotLink {
|
||||
interface SnapshotLink extends PrimitiveBypassTargetRef {
|
||||
primitiveSlot: number
|
||||
targetNodeId: NodeId
|
||||
targetSlot: number
|
||||
}
|
||||
|
||||
interface CohortValidationOk {
|
||||
@@ -665,9 +656,10 @@ function repairPrimitive(
|
||||
}
|
||||
}
|
||||
|
||||
type MigratePreviewResult =
|
||||
| { ok: true; previewName: string }
|
||||
| { ok: false; reason: 'missingSourceNode' | 'missingSourceWidget' }
|
||||
type MigratePreviewResult = Outcome<
|
||||
{ previewName: string },
|
||||
'missingSourceNode' | 'missingSourceWidget'
|
||||
>
|
||||
|
||||
function migratePreview(
|
||||
hostNode: SubgraphNode,
|
||||
@@ -723,15 +715,11 @@ function quarantineFor(
|
||||
const originalEntry: SerializedProxyWidgetTuple = disambiguatingSourceNodeId
|
||||
? [sourceNodeId, sourceWidgetName, disambiguatingSourceNodeId]
|
||||
: [sourceNodeId, sourceWidgetName]
|
||||
const result: ProxyWidgetErrorQuarantineEntry = {
|
||||
return makeQuarantineEntry({
|
||||
originalEntry,
|
||||
reason,
|
||||
attemptedAtVersion: QUARANTINE_VERSION
|
||||
}
|
||||
if (!entry.isHole && entry.hostValue !== undefined) {
|
||||
result.hostValue = entry.hostValue
|
||||
}
|
||||
return result
|
||||
hostValue: entry.isHole ? undefined : entry.hostValue
|
||||
})
|
||||
}
|
||||
|
||||
function appendQuarantine(
|
||||
@@ -762,15 +750,11 @@ export function readHostQuarantine(
|
||||
)
|
||||
}
|
||||
|
||||
interface MakeQuarantineEntryArgs {
|
||||
export function makeQuarantineEntry(args: {
|
||||
originalEntry: SerializedProxyWidgetTuple
|
||||
reason: ProxyWidgetQuarantineReason
|
||||
hostValue?: TWidgetValue
|
||||
}
|
||||
|
||||
export function makeQuarantineEntry(
|
||||
args: MakeQuarantineEntryArgs
|
||||
): ProxyWidgetErrorQuarantineEntry {
|
||||
}): ProxyWidgetErrorQuarantineEntry {
|
||||
const entry: ProxyWidgetErrorQuarantineEntry = {
|
||||
originalEntry: args.originalEntry,
|
||||
reason: args.reason,
|
||||
|
||||
@@ -1169,25 +1169,22 @@ export class SubgraphNode extends LGraphNode implements BaseLGraph {
|
||||
serialized.properties = serializedProperties
|
||||
|
||||
const widgetStore = useWidgetValueStore()
|
||||
const widgetValues: TWidgetValue[] = []
|
||||
let hasSerializableValue = false
|
||||
|
||||
for (const input of this.inputs) {
|
||||
const widgetValues = this.inputs.flatMap((input) => {
|
||||
const widget = input._widget
|
||||
if (!widget || !isPromotedWidgetView(widget)) continue
|
||||
if (!widget || !isPromotedWidgetView(widget)) return []
|
||||
const state = widgetStore.getWidget(
|
||||
rootGraphId,
|
||||
this.id,
|
||||
getPromotedWidgetHostStateName(widget)
|
||||
)
|
||||
const value =
|
||||
state && isWidgetValue(state.value) ? state.value : undefined
|
||||
widgetValues.push(value)
|
||||
hasSerializableValue ||= value !== undefined
|
||||
}
|
||||
return [state && isWidgetValue(state.value) ? state.value : undefined]
|
||||
})
|
||||
|
||||
if (hasSerializableValue) serialized.widgets_values = widgetValues
|
||||
else delete serialized.widgets_values
|
||||
if (widgetValues.some((value) => value !== undefined)) {
|
||||
serialized.widgets_values = widgetValues
|
||||
} else {
|
||||
delete serialized.widgets_values
|
||||
}
|
||||
|
||||
return serialized
|
||||
}
|
||||
|
||||
@@ -72,24 +72,22 @@ export const useAppModeStore = defineStore('appMode', () => {
|
||||
const directNode = rootGraph.getNodeById?.(storedId)
|
||||
if (directNode?.widgets?.some((w) => w.name === widgetName)) return input
|
||||
|
||||
const matches: LinearInput[] = []
|
||||
for (const node of rootGraph.nodes) {
|
||||
if (!(node instanceof SubgraphNode)) continue
|
||||
for (const inputSlot of node.inputs) {
|
||||
const matches: LinearInput[] = rootGraph.nodes.flatMap((node) => {
|
||||
if (!(node instanceof SubgraphNode)) return []
|
||||
return node.inputs.flatMap((inputSlot): LinearInput[] => {
|
||||
const widget = inputSlot._widget
|
||||
if (!widget || !isPromotedWidgetView(widget)) continue
|
||||
if (!widget || !isPromotedWidgetView(widget)) return []
|
||||
if (
|
||||
widget.sourceNodeId === String(storedId) &&
|
||||
widget.sourceWidgetName === widgetName
|
||||
widget.sourceNodeId !== String(storedId) ||
|
||||
widget.sourceWidgetName !== widgetName
|
||||
) {
|
||||
matches.push([
|
||||
createNodeLocatorId(rootGraph.id, node.id),
|
||||
inputSlot.name,
|
||||
input[2]
|
||||
])
|
||||
return []
|
||||
}
|
||||
}
|
||||
}
|
||||
return [
|
||||
[createNodeLocatorId(rootGraph.id, node.id), inputSlot.name, input[2]]
|
||||
]
|
||||
})
|
||||
})
|
||||
if (matches.length === 1) return matches[0]
|
||||
if (matches.length > 1) {
|
||||
console.warn(
|
||||
|
||||
Reference in New Issue
Block a user