6

開始學習node.js和backbone.js,並使用TodoMVC示例作爲我的指南。有幾個部分我有麻煩纏繞我的頭。見下文。瞭解TodoMVC示例

這裏是app.js.

var express = require('express') 
    , http = require('http') 
    , mongoose = require('mongoose') 
    , models = require('./models') 
    , routes = require('./routes') 
    , app = express(); 

app.configure(function() { 
    app.set('views', __dirname + '/views'); 
    app.set('view engine', 'jade'); 
    app.use(express.favicon()); 
    app.use(express.logger('dev')); 
    app.use(require('stylus').middleware({ src: __dirname + '/public' })); 
    app.use(express.static(__dirname + '/public')); 
    app.use(express.bodyParser()); 
    app.use(express.methodOverride()); 
    app.use(app.router); 
}); 

app.configure('development', function() { 
    app.use(express.errorHandler()); 
}); 

routes.init(app); 


mongoose.connect("127.0.0.1", "todomvc", 27017); 

http.createServer(app).listen(3000); 

console.log("Express server listening on port 3000"); 

繼承人是./models:

var mongoose = require('mongoose'), 

    TodoSchema = new mongoose.Schema({ 
    title: { 'type': String, 'default': 'empty todo...' }, 
    order: { 'type': Number }, 
    done: { 'type': Boolean, 'default': false } 
    }); 

module.exports = mongoose.model('Todo', TodoSchema); 

安迪最後,這裏是./routes:

(function (exports) { 

    "use strict"; 

    var mongoose = require('mongoose') 
    , crudUtils = require('../utils/crudUtils') 
    , Todo = mongoose.model('Todo'); 

    function index(req, res) { 
    res.render('index', { 'title': 'Backbone.js, Node.js, MongoDB Todos' }); 
    } 

    exports.init = function (app) { 
    app.get('/', index); 
    crudUtils.initRoutesForModel({ 'app': app, 'model': Todo }); 
    }; 

}(exports)); 

所以我的問題是,如何在貓鼬的 '待辦事項' 模式.model('Todo')在此範圍內可用的路線模塊中?我看到模型模塊正在導出mongoose.model('Todo',TodoSchema);所以我必須相信這是路由模塊如何訪問它,但我不知道爲什麼。我錯過了什麼?我有一種感覺,就是在這種情況下它不完全理解範圍。另外,我不確定讓路由功能匿名的原因。

非常感謝!

回答

8

這是比較令人困惑的事情要處理的節點和貓鼬開始出來的時候有一個。

當您第一次使用require('mongoose')時,它會創建一個singleton Mongoose實例 - 每次您需要時都會返回同一個實例。

這使得它可以很容易的工作,但它是一個有點「神奇」這就是開頭難明白。

這意味着,當你調用app.js mongoose.connect("127.0.0.1", "todomvc", 27017);,它創建與應用程序持續的連接。

這也意味着mongoose.model('Todo', TodoSchema);使Todo模型在任何其他範圍內可用,通過mongoose.model('Todo')調用require('mongoose')。這可能會在上面示例中的另一個文件require的頂部變化,或者在回調過程中需要它的那一刻。

這是怎麼得到的Todo模型到您的routes.js,和一個很好的理由,以確保告訴貓鼬你的模型是你在你的應用程序做的第一件事情之一。

要回答你關於理解範圍的問題;您require的每個文件都有其自己的作用域,並且除訪問全局對象(如進程)外無權訪問任何文件。你必須require你要使用一切,只能通過調用函數或創建經由exports對象公開課傳遞變量英寸

因此對於實際的例子上面有出口從models.js的模式,因爲它不是隨後在應用程序中引用沒有任何好處。在需要models.js的。這是一個在routes.js這些線路,使提供的藤堂模型:在包裹

crudUtils.initRoutesForModel({ 'app': app, 'model': Todo }); 

但也沒有好處(據我所知):

var mongoose = require('mongoose') 
, Todo = mongoose.model('Todo'); // returns the Todo model that was registered by models.js 

這就是藤上的這條線是如何存在因爲這主要由require提供。

+0

非常感謝!這清理了很多。但是,如果我註釋掉'module.exports = mongoose.model(「藤」,TodoSchema);'在models.js,應用程序失敗說「架構尚未註冊模式‘待辦事項’」難道這是爲了將來需要貓鼬而需要的嗎? –

+0

對不起,更清晰,你需要'mongoose.model(「藤」,TodoSchema')'的一部分。這就是用貓鼬註冊模型並使其隨後可用的那一點。我的意思是你可以跳過'module.exports ='部分,因爲你沒有使用你正在導出的內容。此外,你會想用'exports.todoModel = ...'如果你想更多的車型添加到.js文件並導出所有的人,看到http://stackoverflow.com/questions/5311334/what-is - 目的 - nodejs-module-exports-how-do-you-use-it/12907839#12907839關於從模塊導出的更多信息。 –

+0

太棒了!謝謝你的回答!這清理了很多。 –

0

你會想看看快車。

Express是一個極小且靈活的node.js Web應用程序框架,爲構建單頁和多頁以及混合Web應用程序提供了一組強大的功能。

很多你複製的內容並粘貼使用快速腳手架 - 所以它的很多已經預先構建了你,你可以點擊此處查看:http://expressjs.com/

我希望你分的權方向。