目次
AngularJS と Rails の form_for を組み合わせて使ってみました。 何より厄介なのは action 属性 が 自動でついてしまうことです。
環境
- Rails 4.1.8
- Ruby 2.2.2
- AngularJS 1.4.7
- Ubuntu 15.04
状況
Rails の form_for
を使うと、 Rails が action 属性 から すべて 設定してくれます。 もちろん、 form タグ の属性を 追加することもできます。 ただし AngularJS を使う上では問題がありました。
問題になるのは次のコードです。
1 2 3 4 5 |
<%=form_for(@user, html: {'data-ng-submit': 'mainCtrl.create()', novalidate: :novalidate, name: 'createForm'}) do |f|%> <%=f.label :name%> <%=f.text_field :name, required: :required, 'data-ng-model': 'user.name'%> <button>submit</button> <%end%> |
このコードでは、 ボタンをクリックすると AngularJS による処理が実行された後で 本来の form の処理が実行されます。
AngularJS は、 action 属性 がないときは 本来の form の処理を行わないのですが、 Rails で action 属性 が自動でつけられている以上どうしようもありません。 いや、 action 属性 を消す方法があるのかもしれませんが、 私は見つけることができませんでした。
解決法
form タグ に onsubmit="return false;"
を付け加えます。
1 2 3 4 5 |
<%=form_for(@user, html: {'data-ng-submit': 'mainCtrl.create()', novalidate: :novalidate, name: 'createForm', onsubmit: "return false;"}) do |f|%> <%=f.label :name%> <%=f.text_field :name, required: :required, 'data-ng-model': 'user.name'%> <button>submit</button> <%end%> |
button タグ で type="button"
とすると、 ボタンクリック時はどうにか二重処理を防げますが、 入力欄で Enter を押されたときは防げません。
また AngularJS: How to prevent form submission after click on button? に記載されているような方法もありますが、 javascript として 他のところで使えないので、 上に書いたやり方の方がきれいに見えます。