使用Rails 4和AngularJS单页应用程序 [英] Single page application with Rails 4 and AngularJS

查看:165
本文介绍了使用Rails 4和AngularJS单页应用程序的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

好吧,这个想法似乎很有点疯狂,这kindo'是(至少对我来说我的水平)。
我有一个相当standarad Rails应用程序(部分内容网页,博客,新闻块,一些认证)。我希望把它变成一个单页的应用程序。

我想做到的是:


  1. 所有的页面都通过 AJAX 使用 turbolinks ,除了AJAX只返回<$时,像取C $ C>视图部分(在布局产量一部分)withought布局本身,它保持不变(在responces更少的数据,更快的渲染和加载时间)。

  2. 的网页大多只是静态HTML与 AngularJS 标记所以没有太多的处理。

  3. 所有实际的数据是通过JSON分别装入并在视图中填充。

  4. 另外,URL和页面标题得到相应的改变。

我一直在思考这个概念相当长一段时间,我只是似乎无法拿出一个解决方案。在这一点上我必须就如何实现这一actualy可能会有些问题我无法通过一起做了一些想法。任何意见或解决方案大大AP preciated。或者,也许我只是疯了和3个小请求装入都差那么我大的,需要在服务器端完成所有呈现的页面。

所以,这里是我的想法和已知问题。


  1. 当用户第一次访问应用程序,具有角标记的视图模板定期提供,而且第二个请求来自角资源

  2. 然后在ngClick任何链路上ADRESS被发送到内容封装器的ngInclude。

    1. 如何将绑定的onClick上的任何链接,以及如何我可以排除从绑定的某些环节(如链接到外部的认证服务)?

    2. 如何告诉服务器不渲染的布局,如果请求从正在添加角?我虽然增加一个参数的要求,但也有可能是一个更好的主意。


  3. 当ngInclude得到所要求的模板,它触发该模板中的控制器(通常是单个的)的ngInit功能和从服务器获取为JSON数据(与适当的页面标题一起)。

  4. 角填充与接收数据模板,设置浏览器URL的链接的URL,并设置页面标题是什么,它​​只是得了。

    1. 如何更改页面标题和页面的网址?标题可以使用jQuery改变,但有通过角本身呢?一种方法

    2. 同样,我一直在想一些动画,使这一变化更看中的。


  5. 的利润!

所以。你们有什么想的?


解决方案

确定,万一enyone发现过这种想法值得我们思考的。
键可以如下解决。

是否呈现视图或不服务器端的决定。

如果该参数是$ P控制器中的虚假:在 ngInclude

使用一个参数,并设置布局$ psent。
还没有找到一个更简单的方法。

客户端绑定除了那些具有特定类中的所有环节没有AJAX
下面是做它一个指令。

  App.directive('allClicks',函数($解析){
    返回{
      限制:'A',
      transclude:真实,
      更换:真实,
      链接:功能(范围,元素,ATTRS){
        变量$ A = element.find('A')。未($('a.no阿贾克斯'))
            FN = $解析(ATTRS ['allLinks']);
        $ a.on('点击',功能(事件){
          。事件preventDefault();
          范围。$应用(函数(){
            变量$ =这个angular.element(event.target);
            FN(范围,{
              $事件:事件,
              $ HREF:$ this.attr('href属性)
              $链接:$此
            });
          });
        });
      }
    };
  })

然后把它用在一些包装 DIV 标记像&LT;车身NG-控制器=WrapperCtrl全环节=ajaxLink($ HREF)&GT; ,然后在你的内容的div做&LT; D​​IV ID =内容NG-包括=current_page_template&GT;

在你的模板CURRENT_PAGE设置为document.URL角控制器和执行ajaxLink功能。

  $ scope.ajaxLink =功能(路径){
   $ scope.current_page_template =路径+= nolayout真的吗?
}

然后当你得到你的JSON从服务器上的数据,不要忘记使用 history.pushState 来设置URL线和 document.title时= 来SETR称号。

Ok, this idea might seem quite a bit crazy and it kindo' is (at least for me at my level). I have a fairly standarad rails app (some content pages, a blog, a news block, some authentication). And I want to make it into a single page app.

What I want to accomplish is:

  1. All the pages are fetched through AJAX like when using turbolinks, except that the AJAX returns only the view part (the yield part in the layout) withought the layout itself, which stays the same (less data in the responces, quicker render and load time).
  2. The pages are mostly just static html with AngularJS markup so not much to process.
  3. All the actual data is loaded separately through JSON and populated in the view.
  4. Also the url and the page title get changed accordingly.

I've been thinking about this concept for quite a while and I just can't seem to come up with a solution. At this point I've got to some ideas on how this actualy might be done along with some problems I can't pass. Any ideas or solutions are greatly appreciated. Or might be I've just gone crazy and 3 small requests to load a page are worse then I big that needs all the rendering done on server side.

So, here's my idea and known problems.

  1. When user first visits the app, the view template with angular markup is rendered regularly and the second request comes from the Angular Resource.
  2. Then on ngClick on any link that adress is sent to ngInclude of the content wrapper.

    1. How do I bind that onClick on any link and how can I exclude certain links from that bind (e.g. links to external authentication services)?
    2. How do I tell the server not to render the layout if the request is comming from Angular? I though about adding a parameter to the request, but there might be a better idea.

  3. When ngInclude gets the requested template, it fires the ngInit functions of the controllers (usually a single one) in that template and gets the data from the server as JSON (along with the proper page title).
  4. Angular populates the template with the received data, sets the browser url to the url of the link and sets the page title to what it just got.

    1. How do I change the page title and the page url? The title can be changed using jQuery, but is there a way through Angular itself?
    2. Again, I keep thinking about some kind of animation to make this change more fancy.

  5. Profit!

So. What do you guys think?

解决方案

OK, in case enyone ever finds this idea worth thinking about. The key can be solved as follows.

Server-side decision of whether to render the view or not.

Use a param in the ngInclude and set the layout: false in the controller if that param is present. Have not found an easier way.

Client-side binding all links except those that have a particular class no-ajax Here's a directive that does it.

App.directive('allClicks', function($parse) {
    return {
      restrict: 'A',
      transclude: true,
      replace: true,
      link: function(scope, element, attrs) {
        var $a = element.find('a').not($('a.no-ajax')),
            fn = $parse(attrs['allLinks']);
        $a.on('click', function(event) {
          event.preventDefault();
          scope.$apply(function() {
            var $this = angular.element(event.target);
            fn(scope, {
              $event: event,
              $href: $this.attr('href'),
              $link: $this
            });
          });
        });
      }
    };
  }) 

And then use it on some wrapper div or body tag like <body ng-controller="WrapperCtrl" all-links="ajaxLink($href)"> and then in your content div do <div id="content" ng-include="current_page_template">

In your angular controller set the current_page template to the document.URL and implement that ajaxLink function.

$scope.ajaxLink = function(path) {
   $scope.current_page_template = path+"?nolayout=true";
} 

And then when you get your JSON with your data from the server don't forget to use history.pushState to set the url line and document.title = to setr the title.

这篇关于使用Rails 4和AngularJS单页应用程序的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆