How do I pass content from a template to a layout in Express?

后端 未结 6 1593
忘了有多久
忘了有多久 2021-01-31 00:25

I have a basic Express server:

// server.js:
var Express = require(\'express\');
app = Express.createServer();
app.configure(function(){
  app.set(\'views\', Pat         


        
相关标签:
6条回答
  • 2021-01-31 01:05

    Using the tip above about dynamicHelpers, and the magic of closures, I found a fairly elegant solution that works without involving the request object. The trick is to wrap the page title variable in a closure that provides a get() and set() function around it, and make that wrapper object the result of the page_title dynamic helper.

    Create a property.js:

    exports.create = function () {
        var value = null;
        return {
            get: function () {
               return value;
            },
            set: function (new_value) {
               value = new_value;
            }
        };
    }
    

    So calling create() returns an object with a get() and set() method on it, that get and set the closure variable.

    Then, in your app's setup code:

        var property = require("./property.js");
        app.dynamicHelpers ({
            page_title: function () {
             return property.create ();
            }
        });
    

    Since the dynamic helper's value is the result of calling its function, in your view and template, the page_title variable will be the wrapper object with the get() and set() functions.

    In your view, you can then say:

    - page_title.set ("my specific page title");
    

    And in your layout:

    title= page_title.get()
    

    To simplify this a bit further, adding this to property.js:

    exports.creator = function () {
        return function () {
            return exports.create();
        };
    }
    

    Lets you simplify the dynamic helpers declaration block to this:

            var property = require("./property.js");
            app.dynamicHelpers ({
                page_title: property.creator()
            });
    
    0 讨论(0)
  • 2021-01-31 01:09

    You can do that by using this little snippet.

    prop.js:

    var hash = {};
    module.exports = function() {
        return {
            set: function(key, val) { hash[key] = val },
            get: function(key) { return hash[key] }
        };
    };
    

    server.js:

    app.dynamicHelpers({ prop: require(__dirname + '/views/helpers/prop') });
    

    View:

    <% prop.set('foo', 'bar') %>
    

    Layout:

    <%= prop.get('foo') %>
    
    0 讨论(0)
  • 2021-01-31 01:22

    layout.jade

    # the following function is a safe getter/setter for locals
    - function pagevar(key, value) { var undef; return (value===undef) ? locals[key] || null : locals[key] = value; }
    block config
      #intended as a non-rendered block so that locals can be overridden.
      # put your defaults here... - use append in the child view
    !!!
    html
      head
        title=pagevar('title')
        meta(name='description',content=pagevar('description'))
    ...

    page.jade

    append config
      - locals.title = 'override';
      - locals.description = 'override 2';
      - pagevars('somekey', 'some value');
    ...

    Easy peazy.

    0 讨论(0)
  • 2021-01-31 01:24

    Express does not have a preconceived notion of "blocks" or whatever they call that in in rails, but you can use a combination of helpers() and dynamicHelpers() to achieve something similar http://expressjs.com/guide.html#app-helpers-obj-

    Locals passed are available to both the layout and the page view though

    0 讨论(0)
  • 2021-01-31 01:26

    For Express 3 template agnostic, works well with express-partials

    app.use (req, res, next)->
      req.locals = {} unless req.locals
    
      res.locals.content_for = (k, v = null)->
        if !v
          req.locals[k]
        else
          req.locals[k] = v
    
      next()
    
    0 讨论(0)
  • 2021-01-31 01:27

    Pass it in locals: {some: 'Locals', pageTitle: 'Welcome!'}

    0 讨论(0)
提交回复
热议问题