here’s my schema
export const Schema = {
"title": "SQLDatasource",
"description": "--Public API--",
"type": "object",
"properties": {
"type": {
"title": "Type",
"default": "sql",
"enum": ["sql"],
"type": "string"
},
"name": {
"title": "Name",
"type": "string"
},
"assets": {
"title": "Assets",
"default": [],
"type": "array",
"items": {
"anyOf": [
{
"$ref": "#/definitions/TableAsset"
},
{
"$ref": "#/definitions/QueryAsset"
}
]
}
},
},
"required": ["name"],
"additionalProperties": false,
"definitions": {
"TableAsset": {
"title": "TableAsset",
"description": "A _SQLAsset Mixin\n\nThis is used as a mixin for _SQLAsset subclasses to give them the TableAsset functionality\nthat can be used by different SQL datasource subclasses.\n\nFor example see TableAsset defined in this module and SqliteTableAsset defined in\nsqlite_datasource.py",
"type": "object",
"properties": {
"name": {
"title": "Name",
"type": "string"
},
"type": {
"title": "Type",
"default": "table",
"enum": ["table"],
"type": "string"
},
"table_name": {
"title": "Table Name",
"description": "Name of the SQL table. Will default to the value of `name` if not provided.",
"default": "",
"type": "string"
},
"schema_name": {
"title": "Schema Name",
"type": "string"
}
},
"required": ["name"],
"additionalProperties": false
},
"QueryAsset": {
"title": "QueryAsset",
"description": "Base model for most fluent datasource related pydantic models.\n\nAdds yaml dumping and parsing methods.\n\nExtra fields are not allowed.\n\nSerialization methods default to `exclude_unset = True` to prevent serializing\nconfigs full of mostly unset default values.\nAlso prevents passing along unset kwargs to BatchSpec.\nhttps://docs.pydantic.dev/usage/exporting_models/",
"type": "object",
"properties": {
"name": {
"title": "Name",
"type": "string"
},
"type": {
"title": "Type",
"default": "query",
"enum": ["query"],
"type": "string"
},
"query": {
"title": "Query",
"type": "string"
}
},
"required": ["name", "query"],
"additionalProperties": false
}
}
} as const
and here’s my UISchenas for tableAsset
import { JsonFormsUISchemaRegistryEntry, JsonSchema, RuleEffect } from "@jsonforms/core"
import { UISchema } from "./ui-schema"
export const tableAssetUISchema: UISchema = {
type: "VerticalLayout",
elements: [
{
type: "Control",
scope: "#/properties/type",
rule: {
effect: RuleEffect.HIDE,
condition: {},
},
},
{
type: "Control",
scope: "#/properties/name",
label: "Asset name",
},
{
type: "Control",
scope: "#/properties/table_name",
},
],
}
The problem is that inside data
whatever option I select (table asset or query asset) it always sets type to Table
here’s my custom anyOfRenderer
import { useCallback, useState } from "react"
import { Radio, RadioChangeEvent } from "antd"
import {
CombinatorSubSchemaRenderInfo,
createCombinatorRenderInfos,
isAnyOfControl,
JsonFormsRendererRegistryEntry,
JsonSchema,
rankWith,
StatePropsOfCombinator,
} from "@jsonforms/core"
import { JsonFormsDispatch, withJsonFormsAnyOfProps } from "@jsonforms/react"
import styled from "styled-components"
import { CombinatorProperties } from "./CombinatorProperties"
import { startCase } from "lodash-es"
export const AnyOfRendererRegistryEntry: JsonFormsRendererRegistryEntry = {
tester: rankWith(3, isAnyOfControl),
renderer: withJsonFormsAnyOfProps(AnyOfRenderer),
}
const StyledRadioGroup = styled(Radio.Group)`
margin-bottom: ${({ theme }) => theme.spacing.vertical.s};
`
export function AnyOfRenderer({
cells,
indexOfFittingSchema,
path,
renderers,
rootSchema,
schema,
uischema,
uischemas,
visible,
}: StatePropsOfCombinator) {
const [selectedAnyOf, setSelectedAnyOf] = useState<number>(indexOfFittingSchema || 0)
const handleChange = useCallback((e: RadioChangeEvent) => setSelectedAnyOf(e.target.value), [setSelectedAnyOf])
const anyOf = "anyOf"
const anyOfRenderInfos = createCombinatorRenderInfos(
(schema as JsonSchema).anyOf as JsonSchema[],
rootSchema,
anyOf,
uischema,
path,
uischemas,
)
const computeLabel = (anyOfRenderInfo: CombinatorSubSchemaRenderInfo) => {
const label = anyOfRenderInfo.label.startsWith("anyOf") ? anyOfRenderInfo.schema.title : anyOfRenderInfo.label
return startCase(label)
}
return (
<div hidden={!visible}>
<CombinatorProperties schema={schema} combinatorKeyword={anyOf} path={path} />
<StyledRadioGroup
options={anyOfRenderInfos.map((anyOfRenderInfo, index) => ({
// revert this when this is merged & released: https://github.com/eclipsesource/jsonforms/pull/2165#issuecomment-1640981617
label: computeLabel(anyOfRenderInfo),
value: index,
}))}
onChange={handleChange}
value={selectedAnyOf}
/>
{anyOfRenderInfos.map(
(anyOfRenderInfo, anyOfIndex) =>
selectedAnyOf === anyOfIndex && (
<JsonFormsDispatch
key={anyOfIndex}
schema={anyOfRenderInfo.schema}
uischemas={uischemas}
uischema={anyOfRenderInfo.uischema}
path={path}
renderers={renderers}
cells={cells}
/>
),
)}
</div>
)
}
Another issue is that in case I type in “Table fields” some data then switch to Query type and use that fields I get data from all mixed fields and I have no Idea what type (query or table) was selected in UI
As I see in Material renderer and in mine (as it was mostly copied) change of Tab \ Radio happens outside <JsonFormsDispatch />
component. So is there a way to tell <JsonFormsDispatch />
what tab is selected right now?