2

私は、スプロケットとtitのソースコードを掘り下げて、変数/バインディングをErb評価コンテキストに渡す方法を理解しようと多くの時間を費やしてきました。私がやろうとしていることは次のとおりです。リクエストごとに内容が変更されるJSファイルを提供する必要があります。変更される部分はDBに格納されているデータに依存するため、Railsアプリを介してリクエストをルーティングする必要があり、変数/バインディングを渡す必要があります。その上、JSファイルはrequireディレクティブを使用して他のJSファイルを挿入するため、スプロケットを使用する必要があります。

動作していないコードスニペットは次のとおりです。

コントローラファイル:

def ever_changing_js
  @foobars = Foobar.all
  MyApp::Application.assets.instance_eval do
    def foobars
      @foobars
    end
  end

  render :text => MyApp::Application.assets.find_asset('ever_changing.js').to_s, :content_type => "application/javascript"
end

ever_changing.js:

//= require file1.js
//= require file2.js

// Some code that uses @foobars

どうすればこれを行うことができますか?どんな助けでもいただければ幸いです。

4

2 に答える 2

0

I am trying to accomplish the same thing you are. I see a couple problems with your controller code snippet. Rather than doing an instance_eval on the Sprockets::Environment, you should class_eval the context_class, as shown in the Sprockets::Context documentation.

MyApp::Application.assets.context_class.class_eval do
  def foobars
    @foobars
  end
end

Then foobars will be available to your ERb template.

As a sidenote, you can do

render js: MyApp::Application.assets.find_asset('ever_changing.js').to_s

instead of setting the content type yourself.

于 2013-02-01T20:09:29.743 に答える
0

JavaScript ファイルは完全に静的でなければなりません。Sprockets は、あなたがやろうとしていることをするためのものではありません。

リクエストごとに変更されるデータは、<script>レンダリングするテンプレートの下部にあるタグに書き込む必要があります。

アプリ/アセット/javascripts/user.js

(function(exports) {
  function User(name) {
    this.name = name;
  }

  User.prototype.speak() {
    console.log(this.name + ' says, "Hello!"');
  };

  exports.User = User;
})(this);

アプリ/ビュー/ユーザー/show.html.erb

...

  <%= javascript_include_tag('user') %>
  <script>
    (function() {
      var user = new User(<%= @user.name %>);

      $('#speak-button').click(function() {
        user.speak();
      });
    })();
  </script>
</html>

特定のユースケースについてより多くのコンテキストを提供できる場合は、より具体的な例を挙げることができます.

于 2012-11-03T18:16:21.873 に答える