mirror of
https://github.com/Comfy-Org/ComfyUI_frontend.git
synced 2026-04-20 14:30:41 +00:00
## Summary
Architecture documentation proposing an Entity Component System for the
litegraph layer.
```mermaid
graph LR
subgraph Today["Today: Spaghetti"]
God["🍝 God Objects"]
Circ["🔄 Circular Deps"]
Mut["💥 Render Mutations"]
end
subgraph Tomorrow["Tomorrow: ECS"]
ID["🏷️ Branded IDs"]
Comp["📦 Components"]
Sys["⚙️ Systems"]
World["🌍 World"]
end
God -->|"decompose"| Comp
Circ -->|"flatten"| ID
Mut -->|"separate"| Sys
Comp --> World
ID --> World
Sys -->|"query"| World
```
## Changes
- **What**: ADR 0008 + 4 architecture docs (no code changes)
- `docs/adr/0008-entity-component-system.md` — entity taxonomy, branded
IDs, component decomposition, migration strategy
- `docs/architecture/entity-interactions.md` — as-is Mermaid diagrams of
all entity relationships
- `docs/architecture/entity-problems.md` — structural problems with
file:line evidence
- `docs/architecture/ecs-target-architecture.md` — target architecture
diagrams
- `docs/architecture/proto-ecs-stores.md` — analysis of existing Pinia
stores as proto-ECS patterns
## Review Focus
- Does the entity taxonomy (Node, Link, Subgraph, Widget, Slot, Reroute,
Group) cover all cases?
- Are the component decompositions reasonable starting points?
- Is the migration strategy (bridge layer, incremental extraction)
feasible?
- Are there entity interactions or problems we missed?
┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-10420-docs-ADR-0008-Entity-Component-System-32d6d73d365081feb048d16a5231d350)
by [Unito](https://www.unito.io)
---------
Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Co-authored-by: GitHub Action <action@github.com>
Co-authored-by: Amp <amp@ampcode.com>
Co-authored-by: Christian Byrne <cbyrne@comfy.org>
44 lines
1.3 KiB
TypeScript
44 lines
1.3 KiB
TypeScript
import path from 'node:path'
|
|
|
|
export default {
|
|
'tests-ui/**': () =>
|
|
'echo "Files in tests-ui/ are deprecated. Colocate tests with source files." && exit 1',
|
|
|
|
'./**/*.{css,vue}': (stagedFiles: string[]) => {
|
|
const joinedPaths = toJoinedRelativePaths(stagedFiles)
|
|
return [`pnpm exec stylelint --allow-empty-input ${joinedPaths}`]
|
|
},
|
|
|
|
'./**/*.js': (stagedFiles: string[]) => formatAndEslint(stagedFiles),
|
|
|
|
'./**/*.{ts,tsx,vue,mts,json,yaml,md}': (stagedFiles: string[]) => {
|
|
const commands = [...formatAndEslint(stagedFiles), 'pnpm typecheck']
|
|
|
|
const hasBrowserTestsChanges = stagedFiles
|
|
.map((f) => path.relative(process.cwd(), f).replace(/\\/g, '/'))
|
|
.some((f) => f.startsWith('browser_tests/'))
|
|
|
|
if (hasBrowserTestsChanges) {
|
|
commands.push('pnpm typecheck:browser')
|
|
}
|
|
|
|
return commands
|
|
}
|
|
}
|
|
|
|
function formatAndEslint(fileNames: string[]) {
|
|
const joinedPaths = toJoinedRelativePaths(fileNames)
|
|
return [
|
|
`pnpm exec oxfmt --write ${joinedPaths}`,
|
|
`pnpm exec oxlint --fix ${joinedPaths}`,
|
|
`pnpm exec eslint --cache --fix --no-warn-ignored ${joinedPaths}`
|
|
]
|
|
}
|
|
|
|
function toJoinedRelativePaths(fileNames: string[]) {
|
|
const relativePaths = fileNames.map((f) =>
|
|
path.relative(process.cwd(), f).replace(/\\/g, '/')
|
|
)
|
|
return relativePaths.map((p) => `"${p}"`).join(' ')
|
|
}
|