render option forms #628
Labels
No labels
0 points
0.5 points
1 point
13 points
2 points
21 points
3 points
34 points
5 points
55 points
8 points
ambition
application-offering
ambition
configure-applications
ambition
front-end
ambition/install-applications
ambition
security
ambition
switch-host
ambition
update-applications
ambition
user-management
api service
blocked
component: fediversity panel
component: nixops4
documentation
estimation high: >3d
estimation low: <2h
estimation mid: <8h
infinite points
productisation
project-management
question
role: application developer
role: application operator
role: hosting provider
role: maintainer
security
technical debt
testing
type unclear
type: bug
type: deliverable
type: key result
type: objective
type: task
type: user story
user experience
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Blocks
Depends on
#289 key features improving user experience supported
fediversity/fediversity
#610 Configure applications
fediversity/fediversity
#983 panel: Schema limitations due to django-jsonform
fediversity/fediversity
#987 schema-generated forms support
UISchema
fediversity/fediversity
Reference
fediversity/fediversity#628
Loading…
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
As a Fediversity maintainer,
I want to offer schemas to render relevant options,
so that we may present available configuration options to operators.
implementation notes
UISchema(#987)panelpydanticdjango-jsonform(#895, usesreact-jsonschema-form)json-schema-form-elementreact-jsonschema-form(covers draft-07)library comparison
Library comparison
JSON Schema coverage
$refoneOf/anyOfallOfif/then/elsedependencies)dependenciesadditionalPropertiespatternPropertiesUISchema / customization
uiSchemaobjectui:widgethintsHorizontal/Vertical/Group/Categorizationdependencies/oneOfSHOW/HIDE/ENABLE/DISABLE+ JSON-pointer condition)ui:orderFit for Fediversity specifics
attrsOftypes.either/oneOf)RJSF vs JSONForms — feature deep-dive
1.
additionalProperties(NixattrsOf)additionalProperties: <schema>renders the value with its full subschema (soattrsOf submodulegives you a nested form per entry). UX is a list ofkey + valuerows with an Add button; keys are editable text inputs, remove control per row, toggleable viaui:options.expandable. NopropertyNames-style key validation.additionalPropertiesfor the React-Material pack, with an abandoned PR #2494. The Vue/Vuetify pack has working support (PRs #2409, #2481 merged) but with known bugs around mixedproperties+additionalProperties, null/object gaps, and data-insertion-into-wrong-field.Net difference: RJSF gives a working map editor out of the box. JSONForms-React needs a custom renderer (finite cost — a few hundred lines — but a real one).
2.
dependenciesand theenable-gate patterndependenciesis first-class in two flavors."dependencies": { "x": ["y"] }→ ifxis set,ybecomes required (no show/hide, only validation)."dependencies": { "x": { "properties": {...} } }→ dependent properties appear/disappear based on the trigger field's presence.enablegate idiom, the standard pattern isoneOfinside a schema dependency keyed onenable, branching onenum: [true]vsenum: [false]. Verbose but works.dependenciesis not the recommended mechanism — use UISchema Rules: Effects:SHOW/HIDE/ENABLE/DISABLE. Rules can attach to any UI element, soENABLE/DISABLEon aGroupcascades to all its children — the natural fit forenable-gating.Net difference: RJSF expresses the gate in the schema (so a Nix-side codegen can emit it directly). JSONForms expresses it in UISchema rules — cleaner and cascading, but you must auto-generate UISchema alongside the data schema (post-processing
generateDefaultUISchema(schema)to inject rules wherever a sibling is namedenable).3.
oneOf(Nixeither/oneOf)<select>above the variant subform. Labels from each subschema'stitle(or "Option N"). On data load,getMatchingOptionpicks the first subschema whose validation passes — works withconstdiscriminator fields, less well when subschemas overlap. No first-classdiscriminatorkeyword. Customizable viaui:fieldReplacesAnyOrOneOf/OneOfField/AnyOfFieldoverrides.options.detail). AJV-based variant detection. No first-class discriminator either, but tester-based dispatch lets you install one custom renderer matchings.oneOf && s.oneOf.every(v => v.properties?.kind?.const)and apply it across the whole schema.Net difference: small. Both default to dropdowns. JSONForms' tester dispatch makes installing a "tagged-union" widget once-and-everywhere cleaner.
4. Schema diff annotations (#213)
formContext(free-form prop threaded into every field/widget/template). A customFieldTemplatereadsprops.formContext.diff[props.id]and wrapsprops.childrenwith badges. Caveat:props.idis RJSF's dotted-underscores path (root_services_foo_port), not a JSON pointer — you convert.path(dotted) anduischema.scope(which is a JSON pointer, e.g.#/properties/services/properties/foo/properties/port). A high-priorityControlWrapper(rankWith(1000, () => true)) wraps every control and indexesdiff[scope]directly. Diff object delivered via React context (noformContextanalogue, but equivalent).Net difference: both can do it. JSONForms'
scopeis the natural key into a diff object; RJSF'sidneeds translation. Cleaner code on the JSONForms side.5. Dual side-by-side forms with field alignment (#214)
<Form readonly>/<Form disabled>for whole-form,ui:readonly/ui:disabledper-field. Two<Form>instances side-by-side works — but row-level vertical alignment is not built in. Each form derives layout from its own schema; renamed fields (differentids) don't align automatically. You'd write a sharedFieldTemplatewith consistent row heights and orchestrate alignment via CSS-grid yourself.effect: "DISABLE"on aVerticalLayoutdisables everything underneath. Two UISchemas over different data schemas can share layout structure because UISchema is positional and controls reference scopes —old.scope = "#/properties/dbUrl"andnew.scope = "#/properties/databaseUrl"can sit at the same row of eachVerticalLayout. Prior art: Eclipse Theia preferences editor, EclipseSourceEMF.cloudmodel-migration UIs — driving coordinated views off evolving schemas is the use case JSONForms was designed for.Net difference: this is the clearest win. RJSF can be coerced into a migration view but the layout-coordination burden is on you. JSONForms' UISchema-as-layout was designed for exactly this scenario.
Summary
additionalProperties/attrsOfenable-gate (dependencies/ rules)oneOfUXscope-as-JSON-pointer is a cleaner diff key than RJSF'sidThe trade now reads as: RJSF wins decisively on
attrsOftoday (which is pervasive in NixOS — services, users, vhosts). JSONForms wins on every long-term ticket (#213, #214) and on theenableidiom (also pervasive). The JSONForms map-renderer is a finite, one-off engineering cost; the RJSF migration-view coordination is open-ended.kiara referenced this issue2025-12-03 16:41:48 +01:00
UISchemaClosed in #1017.