jsonforms icon indicating copy to clipboard operation
jsonforms copied to clipboard

ref for JsonForms

Open tujger opened this issue 4 years ago • 3 comments

Is your feature request related to a problem? Please describe.

Sometimes i can solve my tasks using the resolved JsonForms object. It would be great to have the access to it using regular React approach - ref.

Describe the solution you'd like

  <JsonForms
      data={data}
      onChange={props => {
          ...
      }}
      ref={ref => {
          console.log(ref)
      }}
      schema={schema}
      uischema={uischema}
  />

Describe alternatives you've considered

Resolve and export current instance with useJsonForms inside any of resolved elements:

export let jfInstance = {};

export default withJsonFormsControlProps(props => {
   jfinstance.current = useJsonForms();
   return <div></div>
})

Framework

React

RendererSet

Material

Additional context

This is not about references in schema.

tujger avatar Oct 25 '21 16:10 tujger

Hi @tujger, interesting request!

Can you elaborate what exactly you are expecting as the content of the ref? From the alternative it looks like it is the current value of the internally maintained context.

Can you elaborate on the use case? What exactly do you need the internally maintained context for?

sdirix avatar Oct 25 '21 16:10 sdirix

Yes, it seems exactly the internal context. So, using it i could update the JF schema or uischema without rerender. In my project i have something like:

  export const Form = (
      {
          data,
          schema,
          uischema
      }: any) => {
 
      return <JsonForms
            data={data}
            schema={schema}
            uischema={uischema}
        />
  }
  
  const mapStateToProps = ({jf}: any) => {
      return {
          uischema: jf.uischema,
          schema: jf.schema
      };
  }
  
  export default connect(mapStateToProps)(Form);

So, uischema and schema can be changed outside of the form, and in this case it causes to re-render the form entirely. Using resolved context i'm waiting for the ability to transfer this context into outside methods and update uischema/schema atomically without re-render.

The specific thing is schema/uischema outside have used to undo/redo stacks and recreated (parse/stringify) each time when they are changed. So, the objects are new on each update of the Form. I'm still thinking how to improve this behavior.

The possible case i see:

export const Form = (
      {
          data,
          schema,
          uischema
      }: any) => {
      const ref = React.useRef();
 
      const onChange = (data, error) => {
         ref.current.dispatch(...);
      }

      return <JsonForms
            data={data}
            ref={ref}
            onChange={onChange}
            schema={schema}
            uischema={uischema}
        />
  }
  
  const mapStateToProps = ({jf}: any) => {
      return {
          //uischema: jf.uischema,
          //schema: jf.schema
      };
  }

tujger avatar Oct 25 '21 16:10 tujger

The only actual thing you would gain is the access to the dispatch method. However almost all of the dispatch use cases are already covered by the JsonForms component. Modifying the context directly without dispatch would break all kinds of memoizations and lead to unexpected behavior.

You can update sub-parts of your JSON Schema also without using dispatch. For example you can use lodash/fp/set to update the relevant part of the current schema and hand the new instance over to JsonForms. This will lead to a minimal amount of rerendering.

Do you have a concrete use case in mind which can't be covered with the current functionality?

sdirix avatar Oct 26 '21 20:10 sdirix

As there was no new information I'll close this issue. Feel free to reopen if you disagree.

sdirix avatar Nov 08 '22 21:11 sdirix