foxhound87 / mobx-react-form

Reactive MobX Form State Management
https://foxhound87.github.io/mobx-react-form
MIT License
1.09k stars 129 forks source link

Usage without classes #272

Closed daedalus28 closed 7 years ago

daedalus28 commented 7 years ago

Great work on this package! We just started working with mobx-react-form, but we use mobx without classes so the class API is unfortunate. It's also a bit unclear why there are 3 places to pass config in to create a form (class methods like on success, schema config like fields, and options like plugins) when they're all json objects without conflicting keys. In the meantime, we've been doing this:

let Form = args => {
  class Form extends MobxReactForm {
    onSuccess = args.onSuccess
    onError = args.onError
  }
  return new Form(args, args)
}

Which allows us to just have a Form function to which we pass all of the options to MobxReactForm and we can pretend there are no classes :smile: It looks something like this:

let formState = Form({
  fields: fieldsFromModelSchema,
  onSuccess: someServiceMethod,
  onError: yellAtUser,
  plugins: {dvr: validatorjs},
})

While this captures our use case, I'm sure there are some options we're missing. It would be awesome if there was a more functional API available for mobx-react-form available from the package itself. Thoughts?

foxhound87 commented 7 years ago

You can actually already move onSuccess and onError out of the class passing an onSubmit object to the second argument of the constructor (to submit the Form Instance), or to the first argument of the constructor (to enable sub-forms submission if you have a nested fields tree).

https://foxhound87.github.io/mobx-react-form/docs/events/validation-handlers/constructor.html#passing-the-validation-handlers-to-the-form-constructor

https://foxhound87.github.io/mobx-react-form/docs/events/validation-handlers/constructor.html#sub-form-submission

daedalus28 commented 7 years ago

That didn't seem to work for me. Based on your comment, I tried doing this:

let Form = ({onSuccess, onError, ...args}) => {
  return new MobxReactForm(args, {onSubmit: { onSuccess, onError }})
}

But then none of the validation rules fired and only onSuccess was called (likely because validation didn't run so there was no error to trigger onError)

foxhound87 commented 7 years ago

Show full form configuration please

foxhound87 commented 7 years ago

The validation handlers are not the issue in your case. The validation rules are not fired because the rules definitions are not passed correctly to the constructor, consequently the onError handler will never be called.

daedalus28 commented 7 years ago

Hey sorry for not responding to this - we've been pushing hard trying to go live with our mobx form stuff so this fell on the backburner. It still does seem like there's no clear way to use this without creating a new class. Our function wrapper creates one on the fly so we can ignore it, but that seems messy. By closing this, does that mean that you're not interested in supporting a functional API?

foxhound87 commented 7 years ago

I can't see any real advantages providing a function instead the class.

You can do it yourself like this:

const makeForm = (fieldsData, formData) => new Form(fieldsData, formData);

then use makeForm in the same way of the original package constructor.