ExpressFrameworkを使用してNode.jsでCMSを作成しています。私のCMSには、ユーザーやページなどのためのいくつかのモジュールがあります。
各モジュールのファイルを、ビューファイルを含む別々のフォルダーに配置する必要があります。どうすればそれを達成できるか知っている人はいますか?
テンプレートエンジンとしてswigを使用していますが、役立つ場合は別のものに置き換えることができます。
最後の更新
複数のビュー フォルダー機能は、Express 4.10 以降のフレームワークでサポートされています。
views
このように、場所の配列をプロパティに渡すだけです。
app.set('views', [__dirname + '/viewsFolder1', __dirname + '/viewsFolder2']);
エクスプレス 2.0
私が知る限り、Express は現時点で複数のビュー パスまたは名前空間をサポートしていません (静的ミドルウェアのように)。
ただし、ルックアップ ロジックを自分で変更して、希望どおりに動作するようにすることもできます。次に例を示します。
function enableMultipleViewFolders(express) {
// proxy function to the default view lookup
var lookupProxy = express.view.lookup;
express.view.lookup = function (view, options) {
if (options.root instanceof Array) {
// clones the options object
var opts = {};
for (var key in options) opts[key] = options[key];
// loops through the paths and tries to match the view
var matchedView = null,
roots = opts.root;
for (var i=0; i<roots.length; i++) {
opts.root = roots[i];
matchedView = lookupProxy.call(this, view, opts);
if (matchedView.exists) break;
}
return matchedView;
}
return lookupProxy.call(express.view, view, options)
};
}
上記の関数を呼び出してパラメーターとしてexpressを渡すことで新しいロジックを有効にすると、構成にビューの配列を指定できるようになります。
var express = require('express');
enableMultipleViewFolders(express);
app.set('views', [__dirname + '/viewsFolder1', __dirname + '/viewsFolder2']);
または、必要に応じて、フレームワークに直接パッチを適用することもできます (その中のview.jsファイルを更新します) 。
これはExpress 2.xで動作するはずですが、新しいバージョン (3.x) で動作するかどうかは不明です
アップデート
残念ながら、 express.viewが定義されていないため、上記のソリューションは Express 3.x では機能しません。
別の可能な解決策は、response.render関数をプロキシし、一致するまでビューフォルダー構成を設定することです。
var renderProxy = express.response.render;
express.render = function(){
app.set('views', 'path/to/custom/views');
try {
return renderProxy.apply(this, arguments);
}
catch (e) {}
app.set('views', 'path/to/default/views');
return renderProxy.apply(this, arguments);
};
私はそれをテストしていませんが、とにかく私には非常にハッキリしているように感じます。残念ながら、この機能は再びプッシュバックされました: https://github.com/visionmedia/express/pull/1186
更新 2
次のプル リクエストがマージされたため、この機能は Express 4.10 に追加されました: https://github.com/strongloop/express/pull/2320
Express 3.x のソリューションは次のとおりです。上記の@ShadowCloudのソリューションと同じルックアップトリックを実行するために、express 3.xの「ビュー」オブジェクトにモンキーパッチを適用します。View
残念ながら、 3.x では公開されていないため、オブジェクトのパス ルックアップはあまりクリーンではありませんexpress
。そのため、node_modules の奥深くまで掘り下げる必要があります。
function enable_multiple_view_folders() {
// Monkey-patch express to accept multiple paths for looking up views.
// this path may change depending on your setup.
var View = require("./node_modules/express/lib/view"),
lookup_proxy = View.prototype.lookup;
View.prototype.lookup = function(viewName) {
var context, match;
if (this.root instanceof Array) {
for (var i = 0; i < this.root.length; i++) {
context = {root: this.root[i]};
match = lookup_proxy.call(context, viewName);
if (match) {
return match;
}
}
return null;
}
return lookup_proxy.call(this, viewName);
};
}
enable_multiple_view_folders();
グロブをインストールnpm install glob
views
次のようなディレクトリがある場合:
views
├── 404.ejs
├── home.ejs
├── includes
│ ├── header.ejs
│ └── footer.ejs
├── post
│ ├── create.ejs
│ └── edit.ejs
└── profile.ejs
このグロブ関数を使用して、ディレクトリ内のサブディレクトリの配列を返すことができますviews
(path.substring
末尾の を削除するには、を追加します/
) 。
let viewPaths = glob.sync('views/**/').map(path => {
return path.substring(0, path.length - 1)
})
console.log(viewPaths)
>> ['views', 'views/post', 'views/includes']
だから今、あなたは設定することができます
app.set('views', viewPaths)
そして今、あなたは使用することができます
res.render('404')
res.render('home')
res.render('post/edit')
res.render('post/create')