0

I'd like to have a a form view that can, depending on circumstances, have submit functionality disabled in a bullet-proof way so that even a clever user could not edit the HTML source (via a browser extension) to re-add the submit button.

It seems one way to do that might be to somehow inject an invalid authenticity token that replaces the (valid) rails-generated one, so that even if a user somehow re-adds the submit button (by editing the HTML via a browser extension) it would still be an invalid submission.

My thought is to have some logic in the view:

- if @form_disabled   # set by controller
  - somehow_invalidate_the_authenticity_token?

How might one 'break' Rails form submission?

The purpose of doing this, instead of rendering the preview in a :show action, is to have the exact same view displaying both the live-form and the dead-form.

jpw
  • 18,697
  • 25
  • 111
  • 187
  • Are you using `form_for`? then use something like `form_for ... authenticity_token: false do |f|` – Aguardientico Sep 30 '15 at 02:11
  • I think that does the opposite of what I want, eg, makes doesn't that make it easier to submit a form, not impossible to submit as I want? – jpw Sep 30 '15 at 02:49
  • If the form does not have the token, then when rails tries to validate it against the one saved in session the controller action will not be called. But the easiest way to verify it is testing, right? – Aguardientico Sep 30 '15 at 03:03

2 Answers2

0

If I were you, I would use pundit.

It's pretty simple, and has few lines of code if you need to know how it works.

I'd start to write the code here, but I realize that the example at the readme fit your needs.

At the application controller add this

At the folder app/policies put the class PostPolicy, of course, you must replace "Post" with the name of your controller in singular (even if you have not a model with that name). The update? (and create?) actions should return true/false to indicate if user is allowed or not.

A few lines down on the readme, you will find the PostsController#update action, which call to authorize with the record before the update. I think you want do the same with create (then you need a create? method at the policy class).

Pundit needs current_user controller method, if you don't have it. Just follow the user customization instructions.

Of course, new and edit actions don't call authorize because they are allowed to everybody. Only the POST & the PUT/PATCH actions are forbidden.

Yes, it's more than a surgery of one line of code. But it's simple and the right way of give access to users.

Alejandro Babio
  • 5,189
  • 17
  • 28
0

After reading my other answer, I start thinking that you can do the same that Pundit does at the controller:

def update
  if <unauthorized user>
    flash[:alert] = "You are not authorized to perform this action."
    redirect_to(request.referrer || root_path)
  else
    # all the update stuff
    # ...
  end
end
Alejandro Babio
  • 5,189
  • 17
  • 28