промежуточное ПО для res.render () при использовании большого количества маршрутов - PullRequest
0 голосов
/ 10 ноября 2018

Я создал веб-страницу, чтобы использовать ее локально. У меня есть тонна маршрутов, таких как показанные ниже - 31 .ejs файлов и 3 .html файлов. (Они все находятся в одной папке "views").

//app.js - using node and express
    app.get('/page1', function(req, res){
        res.render('page1');
    });
    app.get('/page2', function(req, res){
        res.sendFile('views/page2.html', { root: __dirname });
    });

Я использую app.get для каждого из этих файлов. У меня было ощущение, что это не СУХОЙ код, и теперь я пытаюсь найти более элегантный и оптимальный способ достижения того же результата.

  • Я знаю, что многие res.sendFile(); могут быть заменены одним оператором промежуточного программного обеспечения express.static(). Я обычно использую express.static() в «общедоступной» папке, которую я использую для сохранения всех своих css-файлов - например, app.use(express.static(path.join(__dirname, 'public')));. Но я все еще не понимаю, как я мог бы использовать это, чтобы упростить все мои res.sendFile().

  • Что касается многих res.render(); маршрутов, я знаю, что, если я не передам никаких настроенных данных, я, вероятно, мог бы заменить их одним промежуточным программным обеспечением, которое обрабатывает либо весь каталог файлов шаблонов (и их соответствующие маршруты ) или список файлов. Я просто не знаю, как бы я это сделал.


Любая помощь очень ценится, спасибо!


[UPDATE]
  • richie
  • node_modules
  • public
  • css-файлы, изображения и т. Д.
просмотров
  • частичные
  • все частичные файлы
программирование Public
  • все файлы ejs из той же темы
другие файлы (html и другие ejs) appjs packagejson package-lockjson



const express = require('express');
const bodyParser = require('body-parser');
const path = require('path');

const app = express(); 

// Body Parser Middleware
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({extended: false}));

// engine
app.set("view engine", "ejs");

// Set static path
app.use(express.static(path.join(__dirname, 'public')));

const fs = require('fs');

function renderStatic(dir) {
    return function(req, res, next) {
        let target = path.join(dir, req.path);
        fs.access(target, fs.constants.R_OK, function(err) {
            if (err) {
                // file not found, just move on
                next();
            } else {
                res.render(target);
            }
        });
    }
}

app.use(renderStatic(path.join(__dirname, "views/programmingPublic")));

Ниже приведен формат моего бокового меню: (все эти файлы находятся в папке «softwarePublic»)

<a href="/programming" class="title">Programming</a>
<li><a href="/c">C</a></li>
<li><a href="/cpp">C++</a></li>
<li><a href="/python">Python</a></li>
<li><a href="/javascript">JavaScript</a></li>
<li><a href="/php">PHP</a></li>

1 Ответ

0 голосов
/ 10 ноября 2018

Если у вас есть куча страниц, которые должны вызывать res.render(), но вы не передаете пользовательские параметры для каждого рендера, вы можете изолировать все эти шаблоны в их собственном каталоге, а затем использовать некоторое промежуточное программное обеспечение, например:

const path = require('path');
const fs = require('fs');

function renderStatic(dir, options) {
    const regex = /^\.|\.\.|\/\.|\\\./;
    options = options || {};

    return function(req, res, next) {
        let target = path.join(dir, req.path);
        if (options.ext && !path.extname(target)) {
           target = target + options.ext;
        }
        // don't allow leading dot or double dot anywhere in the path
        if (regex.test(target)) {
           next();
           return;
        }
        fs.access(target, fs.constants.R_OK, function(err) {
            if (err) {
                // file not found, just move on
                next();
            } else {
                res.render(target);
            }
        });
    }
}

app.use(renderStatic(path.join(__dirname, "renderPublic"), {ext: ".ejs"}));

Обратите внимание, что вы должны изолировать эти файлы шаблонов в их собственном каталоге, чтобы другие файлы там не находились.

Для полноты безопасности этот код также должен отфильтровывать элементы . и .. в пути, как express.static(), чтобы не дать злоумышленнику подняться по иерархии каталогов, чтобы получить доступ к другим файлам, чем те, которые находятся в визуализировать статический каталог.


Затем для маршрутов, которые вы используете res.sendFile() и никакой другой логики, просто изолируйте эти HTML-файлы в их собственном каталоге и укажите express.static() в этом каталоге. Затем промежуточное ПО express.static() найдет соответствующий HTML-файл в этом каталоге и автоматически сделает для вас res.sendFile(), точно так же, как это делается для ваших CSS-файлов.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...