Sails.js 将数据从局部控制器发送到局部视图 [英] Sails.js send data from partial controller to partial view

查看:47
本文介绍了Sails.js 将数据从局部控制器发送到局部视图的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我是sails.js 的新手.我曾在 opencart 上工作过.在sails.js 中,我们如何重用动态类别等功能(基于表格数据).所以在这种情况下会有一个菜单控制器和 menu.ejs 视图.我需要的是有一个父控制器和一个像 HomeController.js 和 HomeView.ejs 这样的父视图.在该菜单部分内将被重用.与页眉控制器/视图、页脚控制器/视图相同.因此,如果我路由到/home",那么它将调用 HomeController.js.然后 home 将加载 headerController 这会将数据发送到 headerView.现在 headerController 将调用 menuController 和 menuController 将数据传递给 menuView.请帮我解决这个问题.提前致谢.

解决方案

您不能嵌套控制器调用,因为 您将在每个方法中调用的 res.view() 方法是终端.

<块引用>

这个方法是终端,意思是一般是最后一行代码您的应用应针对给定请求运行

控制器不渲染视图,它们向客户端调用诸如 res.view()res.json() 之类的方法发送 http 响应.<小时>

对于您正在谈论的 HeaderController,我想内容是静态的,您应该将内容写入 布局.

<小时>

关于MenuController,我知道菜单可能会根据请求而改变,您不一定要构建单页应用程序,并且一旦页面被调用,您可能不想通过 AJAX 或 websocket 调用它加载.要以类似于您的描述的方式解决它,您可以使用独立于控制器呈现视图的可能性.

您可以创建一个服务来执行它:

//api/service/partials.js模块.出口 = {/*** 渲染菜单并将结果传递给回调 cb(err, html)* "req" 参数存在于控制器方法中,但不是 "res"* "data" 可以是传递额外配置的可选参数*/菜单:功能(请求,数据,CB){//这里写下根据请求构建菜单的逻辑//访问 express 应用以呈现menu.ejs"模板//参见 http://expressjs.com/3x/api.html#app.renderSails.hooks.http.app.render('menu', data, cb);}};

要渲染的模板示例:

<!-- views/menu.ejs -->这是菜单<%=数据%>

此时,您可以简单地在所有控制器中调用 partials.menu(req, data, function(err, html) {}) 并将生成的 html 注入控制器视图中.但这将是很多重复的代码.让我们编写一个 policy 来执行它:

//api/policies/dynamicMenu.jsmodule.exports = function(req, res, next) {//调用生成菜单内容的服务//并将结果注入到控制器模板中可访问的菜单"变量中partials.menu(req, {data: 'data test'}, function(err, html) {res.locals.menu = html;下一个();});};

您可以为每个部分"编写一个策略(例如:一个用于菜单,另一个用于页脚......).将 policy 应用于控制器:

//config/policies.jsmodule.exports.policies = {//...//将策略应用于显示菜单的控制器'aControllerThatDisplaysTheMenu':{'*': ['动态菜单']}//...}

最后,在布局文件中显示菜单:

<!-- views/layout.ejs -->...<%=菜单%>...

这只是一个简单的示例,您必须处理错误并对其进行调整以更好地满足您的需求.

I am new in sails.js. I have worked on opencart. In sails.js, How can we reuse functionality like dynamic categories (based on the tables data). So in this case there will be a menu controller and menu.ejs view. What i need is there will be a parent controller and a parent view like HomeController.js and HomeView.ejs . Inside that menu part will be reuse. same like header controller/view , footer controller/view . So if i route to '/home' then it will call HomeController.js. Then home will load headerController this will send data to headerView. Now headerController will call menuController and menuController pass data to menuView. Please help me on this. Thanks in advance.

解决方案

You cannot nest controller calls since the res.view() method that you would call in each one of them is terminal.

This method is terminal, meaning it is generally the last line of code your app should run for a given request

The controllers do not render a view, they send an http response to the client calling methods like res.view() or res.json().


For the HeaderController you are talking about, I guess the content is static and you should just write the content in the layout.


About the MenuController, I understand a menu may change depending on the request, you are not necessarily building a single page application and you may not want to call it by AJAX or websocket once the page is loaded. To solve it in a manner similar to your description, you can use the possibility to render views independently from controllers.

You could create a service to perform it:

// api/service/partials.js
module.exports = {

  /**
   * Renders the menu and pass the result in a callback cb(err, html)
   * The "req" argument is present like in a controller method, but not "res"
   * "data" could be an optional argument to pass extra configuration
   */
  menu: function(req, data, cb) {
    // Write here the logic to build the menu depending on the request 

    // Access to the express app to render the "menu.ejs" template
    // see http://expressjs.com/3x/api.html#app.render
    sails.hooks.http.app.render('menu', data, cb);
  }

};

Example of template to render:

<!-- views/menu.ejs -->
This is the menu <%= data %>

At this point, you could simply call partials.menu(req, data, function(err, html) {}) in all your controllers and inject the generated html in the controller's view. But that would be a lot of duplicate code. Let's write a policy to perform it:

// api/policies/dynamicMenu.js
module.exports = function(req, res, next) {

  // Call the service that generate the content of the menu
  // and inject the result in a "menu" variable accessible in the controller's template
  partials.menu(req, {data: 'data test'}, function(err, html) {
    res.locals.menu = html;
    next();
  });

};

You could write one policy per "partial" (ex: one for the menu, another one for the footer ...). Apply the policy to controllers:

// config/policies.js
module.exports.policies = {
  // ...

  // Apply the policy to controllers that display the menu
  'aControllerThatDisplaysTheMenu': {
    '*': ['dynamicMenu']
  }

  // ...
}

Finally, display the menu in your layout file:

<!-- views/layout.ejs -->
...
<%= menu %>
...

This is just a quick example, you have to handle errors and adapt it to better fit your needs.

这篇关于Sails.js 将数据从局部控制器发送到局部视图的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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