@ericrisco/rsc 3.3.1 → 3.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (61) hide show
  1. package/README.md +3 -3
  2. package/manifest.json +43 -22
  3. package/package.json +1 -1
  4. package/scripts/lib/default-skill-floor.js +5 -1
  5. package/scripts/lib/domains.js +2 -2
  6. package/scripts/lib/retired-skills.js +4 -0
  7. package/scripts/rsc.js +1 -1
  8. package/skills/design/SKILL.md +4 -3
  9. package/skills/design/evals/cases.yaml +2 -2
  10. package/skills/ftd/SKILL.md +1 -1
  11. package/skills/react/SKILL.md +2 -1
  12. package/skills/ux/SKILL.md +149 -0
  13. package/skills/ux/THIRD_PARTY.md +32 -0
  14. package/skills/ux/evals/cases.yaml +40 -0
  15. package/skills/ux/references/flows.md +124 -0
  16. package/skills/ux/upstream/UPSTREAM.json +59 -0
  17. package/skills/ux/upstream/ux-designer/GUIDE.md +180 -0
  18. package/skills/ux/upstream/ux-designer/LICENSE +21 -0
  19. package/skills/ux/upstream/ux-designer/references/01-core-principles.md +251 -0
  20. package/skills/ux/upstream/ux-designer/references/02-laws-of-ux.md +330 -0
  21. package/skills/ux/upstream/ux-designer/references/03-accessibility.md +411 -0
  22. package/skills/ux/upstream/ux-designer/references/04-visual-design.md +433 -0
  23. package/skills/ux/upstream/ux-designer/references/05-information-architecture.md +432 -0
  24. package/skills/ux/upstream/ux-designer/references/06-interaction-design.md +495 -0
  25. package/skills/ux/upstream/ux-designer/references/07-forms-and-inputs.md +491 -0
  26. package/skills/ux/upstream/ux-designer/references/08-mobile-ux.md +539 -0
  27. package/skills/ux/upstream/ux-designer/references/09-ux-writing.md +493 -0
  28. package/skills/ux/upstream/ux-designer/references/10-user-research.md +533 -0
  29. package/skills/ux/upstream/ux-designer/references/11-design-systems.md +618 -0
  30. package/skills/ux/upstream/ux-designer/references/12a-presence-awareness.md +395 -0
  31. package/skills/ux/upstream/ux-designer/references/12b-conflict-resolution-sync.md +420 -0
  32. package/skills/ux/upstream/ux-designer/references/13a-canvas-navigation.md +388 -0
  33. package/skills/ux/upstream/ux-designer/references/13b-canvas-objects-performance.md +559 -0
  34. package/skills/ux/upstream/ux-designer/references/14-ai-ux-patterns.md +511 -0
  35. package/skills/ux/upstream/ux-designer/references/15-ethical-design.md +419 -0
  36. package/skills/ux/upstream/ux-designer/references/16-onboarding.md +430 -0
  37. package/skills/ux/upstream/ux-designer/references/17-notifications.md +461 -0
  38. package/skills/ux/upstream/ux-designer/references/18-data-visualization.md +453 -0
  39. package/skills/ux/upstream/ux-designer/references/19-search-ux.md +479 -0
  40. package/skills/ux/upstream/ux-designer/references/20-emotional-design.md +382 -0
  41. package/skills/ux/upstream/ux-designer/references/21-data-tables.md +629 -0
  42. package/skills/ux/upstream/ux-designer/references/22-performance-ux.md +626 -0
  43. package/skills/ux/upstream/ux-designer/references/23-internationalization.md +347 -0
  44. package/skills/ux/upstream/ux-designer/references/24-voice-and-multimodal.md +308 -0
  45. package/skills/ux/upstream/ux-designer/references/25a-barcode-camera-scanning.md +342 -0
  46. package/skills/ux/upstream/ux-designer/references/25b-barcode-scanner-workflows.md +412 -0
  47. package/skills/ux/upstream/ux-designer/references/25c-barcode-display.md +277 -0
  48. package/skills/ux/upstream/ux-usability-foundations/GUIDE.md +285 -0
  49. package/skills/ux/upstream/ux-usability-foundations/LICENSE +21 -0
  50. package/skills/ux/upstream/ux-usability-foundations/references/anti-patterns.md +267 -0
  51. package/skills/ux/upstream/ux-usability-foundations/references/checklists.md +130 -0
  52. package/skills/ux/upstream/ux-usability-foundations/references/decision-prompts.md +340 -0
  53. package/skills/ux/upstream/ux-usability-foundations/references/principle-cards.md +449 -0
  54. package/skills/worktrees/SKILL.md +19 -5
  55. package/targets/branch-guard.mjs +59 -4
  56. package/targets/clone-bootstrap.mjs +1 -1
  57. package/targets/session-memory-adapter.mjs +2 -2
  58. package/targets/team-safe-start.mjs +1 -0
  59. package/targets/worktree-reaper.mjs +14 -1
  60. package/skills/ui-engineering/SKILL.md +0 -113
  61. package/skills/ui-engineering/evals/cases.yaml +0 -38
@@ -1,113 +0,0 @@
1
- ---
2
- name: ui-engineering
3
- description: "Use when the question is how interface should be BUILT — component boundaries, state that belongs in the URL vs the component, loading/empty/error states, forms, optimistic updates, build vs adopt. NOT the visual system (`design`), NOT framework mechanics (`react`/`nextjs`)."
4
- tags: [interface, frontend, architecture, components, state, craft]
5
- recommends: [design]
6
- profiles: [core, full]
7
- origin: risco
8
- ---
9
-
10
- # UI engineering — the decisions between the design and the framework
11
-
12
- There is a layer that neither the design skill nor the framework skill owns. The design says what
13
- the screen should be. The framework says how its API works. **In between sits every decision that
14
- makes an interface either durable or a maintenance tax** — and it is where most interface work
15
- actually goes wrong.
16
-
17
- Nothing here is framework-specific. These decisions are the same in React, Vue, Svelte, SwiftUI and
18
- plain HTML; only the syntax moves.
19
-
20
- ## The one rule
21
-
22
- **State goes to the outermost place that still needs it, and no further.** Almost every interface
23
- tangle is that rule broken in one of two directions: state hoarded in a component that others need,
24
- or state hoisted into a global store that only one component ever reads.
25
-
26
- | Where the state lives | When that is right |
27
- | --- | --- |
28
- | **The URL** | Anything a user would bookmark, share, or expect the back button to restore: filters, tabs, pagination, the open item |
29
- | **The server** | Anything that outlives the session or belongs to more than one user |
30
- | **A shared parent** | Two siblings genuinely need it, and it dies with the screen |
31
- | **The component** | Nobody else reads it: hover, focus, an open menu, an in-flight draft |
32
-
33
- The most common and most expensive mistake is the first row: state that belongs in the URL kept in a
34
- component. It looks fine until someone reloads, shares a link, or presses back — and then the
35
- interface silently loses what the user did.
36
-
37
- ## Every state, not just the happy one
38
-
39
- An interface is not finished when it renders data. It is finished when it renders **all five**:
40
-
41
- | State | The question it answers | The usual failure |
42
- | --- | --- | --- |
43
- | **Loading** | "Is it working?" | A spinner where the shape is already known — use the shape |
44
- | **Empty** | "Is it broken, or is there nothing?" | Blank. It must say which, and what to do next |
45
- | **Error** | "What now?" | A message with no action. Every denial carries its own way out |
46
- | **Partial** | "Some of it failed" | Ignored entirely; the screen shows a half-truth |
47
- | **Success** | "It worked" | Silence, so the user does it twice |
48
-
49
- The empty state is the one that gets skipped, and it is the first state a new user ever sees.
50
-
51
- ## Component boundaries
52
-
53
- A component earns its existence by **hiding a decision**, not by being reused. Splitting for reuse
54
- alone produces the worst interfaces: a wrapper around a wrapper, each passing props through, none
55
- owning anything.
56
-
57
- Draw the boundary where:
58
-
59
- - it owns a piece of state nothing outside needs;
60
- - it can be described in one sentence without "and";
61
- - swapping its internals changes nothing outside it.
62
-
63
- Do **not** draw a boundary because a file is long. Long is not a defect; a file that does two
64
- unrelated things is, and it is usually short.
65
-
66
- ## Forms
67
-
68
- Forms are where interfaces most often insult people, and the rules are unglamorous:
69
-
70
- - **Validate on blur, not on keystroke.** Telling someone their email is invalid while they are on
71
- the third character is scolding them for not having finished.
72
- - **Never clear what they typed.** Not on error, not on refresh, not on navigation. Their input is
73
- theirs.
74
- - **Disable the submit only while submitting**, never as a way of enforcing validity — a disabled
75
- button with no reason is a dead end.
76
- - **The error goes next to the field**, and says what to do, not what is wrong.
77
-
78
- ## Optimistic updates
79
-
80
- Show the result before the server confirms **only** when you can honestly undo it. That means: the
81
- operation is idempotent, the failure is rare, and reverting it is visible and comprehensible.
82
-
83
- Optimism on a destructive or an expensive action is a lie you will have to retract in front of the
84
- user. Deleting, paying, sending — those wait.
85
-
86
- ## Build or adopt
87
-
88
- Adopting a component costs bundle size, an API you did not design, and an upgrade you will owe
89
- later. Building costs the accessibility work you will get wrong.
90
-
91
- The split is not about difficulty, it is about **who is the authority on the behaviour**:
92
-
93
- - **Adopt** for behaviour with a specification you would otherwise be reimplementing badly: focus
94
- trapping, combobox semantics, date handling, virtualisation.
95
- - **Build** for anything that is your product's own logic wearing a UI, or where the library gives
96
- you 60% and you fight the remaining 40% forever.
97
-
98
- ## Anti-patterns → STOP
99
-
100
- | If you're about to… | Reality / Fix |
101
- | --- | --- |
102
- | Put a filter or tab selection in component state | It belongs in the URL. Reload, share and back are part of the interface. |
103
- | Add a global store because passing props feels tedious | Tedious is not broken. Global state that one component reads is a leak with ceremony. |
104
- | Ship a screen with only the loaded state | Loading, empty, error and partial are not extras. The empty one is what a new user sees first. |
105
- | Split a component because the file got long | Length is not the defect. Two unrelated responsibilities are, and they are usually short. |
106
- | Show a delete as done before the server confirms | Optimism on a destructive action is a lie you will retract in public. |
107
- | Reach here for how the framework's hooks work | That is `../react/SKILL.md` or `../nextjs/SKILL.md`. This skill decides what to build; those decide how to express it. |
108
-
109
- ## See Also
110
-
111
- - `../design/SKILL.md` — the visual system these decisions serve, its motion layer, and the
112
- browser-measured critique that judges the result.
113
- - `../accessibility/SKILL.md` — the ground under focus, semantics and forms.
@@ -1,38 +0,0 @@
1
- skill: ui-engineering
2
-
3
- should_trigger:
4
- - prompt: "Where should the filter state live — component, context or the URL?"
5
- why: "The canonical case: the one rule this skill exists to apply."
6
- - prompt: "How should I split these components? The file is getting big."
7
- why: "Component boundaries, and the file-length premise is one this skill corrects."
8
- - prompt: "We only render the loaded state. What else does this screen need?"
9
- why: "The five states are the checklist this skill owns."
10
- - prompt: "¿Valido el formulario mientras escribe o al salir del campo?"
11
- why: "Form behaviour, in Spanish; the trigger is the decision, not the language."
12
- - prompt: "Should I use a component library for the date picker or build it?"
13
- why: "Build vs adopt, decided by who owns the behaviour's specification."
14
- - prompt: "Can we show the delete as done immediately and roll back if it fails?"
15
- why: "Optimistic updates, and this is the case where the answer is no."
16
-
17
- should_not_trigger:
18
- - prompt: "Design the pricing page — layout, type scale, the colour system."
19
- route_to: "design"
20
- why: "The visual system is decided before this layer has anything to build."
21
- - prompt: "My useEffect runs twice in development and I don't understand why."
22
- route_to: "react"
23
- why: "Framework mechanics. This skill decides what to build, not how the framework behaves."
24
- - prompt: "The dropdown animation feels cheap, what duration should it use?"
25
- route_to: "design"
26
- why: "Once the component exists, how it moves is motion craft."
27
- - prompt: "Grade this dashboard and tell me if it is actually good."
28
- route_to: "design"
29
- why: "Judging a finished screen is the critique loop, not the build decisions."
30
- - prompt: "Set up the Next.js App Router with server actions for this project."
31
- route_to: "nextjs"
32
- why: "Stack setup is the stack skill's; this one is framework-agnostic by construction."
33
-
34
- capability:
35
- - prompt: "Our search page keeps its query and filters in component state. Users complain the back button loses everything. What is wrong and what is the fix?"
36
- why: "The single most expensive instance of the one rule, stated as a real symptom rather than as theory."
37
- - prompt: "This list screen shows a spinner, then rows. What states are we missing and why does each matter?"
38
- why: "Forces the five-state checklist, including the empty state that a new user sees first."